/** * Gets all characters for a bracket */ public static function getByBracketId($bracketId) { $retVal = null; if (is_numeric($bracketId)) { $cacheKey = 'Character_getByBracketId_' . $bracketId; $retVal = Lib\Cache::Get($cacheKey); if (false === $retVal) { $retVal = null; // TODO - make order by column configurable $retVal = Character::queryReturnAll(['bracketId' => $bracketId], ['source' => 'ASC', 'name' => 'ASC']); Lib\Cache::Set($cacheKey, $retVal); } } return $retVal; }
/** * Generates a list of characters in a bracket (ordered by seed) and their performance * in said bracket */ public static function getEntrantPerformanceStats(Bracket $bracket, $force = false) { return Lib\Cache::fetchLongCache(function () use($bracket) { // Get all tourney rounds and characters for this bracket $characters = Character::queryReturnAll(['bracketId' => $bracket->id, 'seed' => ['null' => false]], ['seed' => 'asc']); $rounds = Round::queryReturnAll(['bracketId' => $bracket->id, 'final' => 1, 'tier' => ['gt' => 0]], ['id' => 'asc']); // Create a hash out of the characters $temp = []; foreach ($characters as $character) { $temp[$character->id] = $character; } $characters = $temp; // Sort the rounds out based on character for faster access later $characterRounds = []; foreach ($rounds as $round) { // Decorate the round with full character models $round->character1 = $characters[$round->character1Id]; $round->character2 = $characters[$round->character2Id]; self::_addRoundToCharacterRounds($round, $round->character1Id, $characterRounds); self::_addRoundToCharacterRounds($round, $round->character2Id, $characterRounds); } $retVal = []; foreach ($characters as $character) { $roundsForCharacter = array_values($characterRounds[$character->id]); $closestDiff = -1; $closestRound = null; $lostTo = null; $totalVotes = 0; foreach ($roundsForCharacter as $round) { // Heheheh... so gross $isCharacter1 = $round->character1Id == $character->id; $totalVotes += $isCharacter1 ? $round->character1Votes : $round->character2Votes; $diff = abs($round->character1Votes - $round->character2Votes); if ($diff < $closestDiff || $closestDiff === -1) { $closestDiff = $diff; // This case should be small enough that re-instantiating through a loop // shouldn't prove too much of a performance concern (especially since // it's generated only once per new round). Will monitor in production $closestRound = (object) ['character' => $isCharacter1 ? $round->character2 : $round->character1, 'difference' => $closestDiff, 'round' => $round]; } $lost = $isCharacter1 && $round->character1Votes < $round->character2Votes || !$isCharacter1 && $round->character2Votes < $round->character1Votes; $lostTo = $lost ? (object) ['character' => $isCharacter1 ? $round->character2 : $round->character1, 'lostBy' => $diff, 'round' => $round] : null; } $retVal[] = (object) ['character' => $character, 'closestRound' => $closestRound, 'lostTo' => $lostTo, 'totalVotes' => $totalVotes, 'group' => chr(65 + $roundsForCharacter[0]->group)]; } return $retVal; }, 'Stats::PerformanceStats_' . $bracket->id, $force); }
private static function _autoProcessNominees(Api\Bracket $bracket) { // Get all characters and nominees in this bracket $characters = Api\Character::queryReturnAll(['bracketId' => $bracket->id]); $nominees = Api\Nominee::queryReturnAll(['bracketId' => $bracket->id]); $count = 0; if ($characters && $nominees) { // Hash maps for fast tracking of nominees/characters entered // The hash id is Name + Source $verifiedHash = []; $nomineesHash = []; foreach ($characters as $character) { $key = self::_normalizeString($character->name) . '_' . self::_normalizeString($character->source); $verifiedHash[$key] = true; } foreach ($nominees as $nominee) { $key = self::_normalizeString($nominee->name) . '_' . self::_normalizeString($nominee->source); // If this nominee is marked as processed, add it to the verified hash if ($nominee->processed) { $verifiedHash[$key] = true; } else { // First, check to see if this has a verified counterpart if (isset($verifiedHash[$key])) { if (!isset($nomineesHash[$key])) { $nomineesHash[$key] = [$nominee->id]; $count++; } } else { // See if there's another nominee similar to this one. // If so, add this nominee to the IDs to mark as processed. // Otheriwse, note that this name has turned up, but we want to leave this one unprocessed if (isset($nomineesHash[$key])) { $nomineesHash[$key][] = $nominee->id; $count++; } else { $nomineesHash[$key] = []; } } } } if (count($nomineesHash)) { // Merge all the ID arrays down to one array of IDs $nomineeIds = []; foreach ($nomineesHash as $key => $ids) { $nomineeIds = array_merge($nomineeIds, $ids); } // Mark as processed Api\Nominee::markAsProcessed($nomineeIds); } } self::_displayNominations($bracket, false, $count . ' duplicate nominee' . ($count !== 1 ? 's' : '') . ' were processed'); }