Skip to content

Instantly share code, notes, and snippets.

@marcelotk15
Last active September 14, 2022 03:20
Show Gist options
  • Save marcelotk15/6dc77bd8a2e867d6fbca920382dcab7a to your computer and use it in GitHub Desktop.
Save marcelotk15/6dc77bd8a2e867d6fbca920382dcab7a to your computer and use it in GitHub Desktop.
Combinação de times - T = n jogadores tomado de e p em p, tal que Ti vs Tj não repita nenhum ni. i, j = índices.
const PLAYERS = [1, 2, 3, 4]
const TEAM_SIZE = 2;
function fatorial(n) {
if (n === 0) return 0;
if (n < 0) return NaN;
return n === 1 ? 1 : fatorial(n - 1) * n;
}
function simpleCombinations(n, p) {
return p > n ? 0 : fatorial(n) / (fatorial(p) * (fatorial(n-p)))
}
function combinations(arr, p, prefix = []) {
return p == 0 ? [prefix] : arr.flatMap((item, i) =>
combinations(arr.slice(i + 1), p - 1, [...prefix, item])
);
}
function matchesCombinations(arr, p, prefix = []) {
return p == 0 ? [prefix] : arr.flatMap((teamA, i) =>
matchesCombinations(arr.slice(i + 1).filter(teamB => !teamA.some(player => teamB.includes(player))), p - 1, [...prefix, teamA])
);
}
console.log('total de times possíveis', simpleCombinations(PLAYERS.length, TEAM_SIZE));
console.log('times possíveis', combinations(PLAYERS, TEAM_SIZE));
console.log('confrontos', matchesCombinations(combinations(PLAYERS, TEAM_SIZE), 2));
@rafaelcascalho
Copy link

I personally liked the use of recursion, since it uses divide and conquer and make sure every call has only its own context.

A possible suggestion, if you're interested in performance improvement, would be to use a dictionary to hold the mounted teams, and not necessarily use filter and includes, cause they both use list operations, and those looks could be improved by simply having them mapped to a dict with the following structure:

const teams = {
  teamA: { playerNumber: true },
  teamB: { playerNumber: true }
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment