Quem é o rei do torneio?


13

fundo

Considere um torneio round-robin, no qual cada competidor joga um jogo contra todos os outros competidores. Não há empates, então cada jogo tem um vencedor e um perdedor. Um competidor Um é um rei do torneio, se por qualquer outro concorrente B , ou A batida B ou A derrotou outro concorrente C , que por sua vez batida B . Pode ser demonstrado que todo torneio tem pelo menos um rei (embora possa haver vários). Neste desafio, sua tarefa é encontrar os reis de um determinado torneio.

Entrada e saída

Sua entrada é uma N × Nmatriz booleana Te, opcionalmente, o número N ≥ 2de concorrentes. Cada entrada T[i][j]representa o resultado do jogo entre competidores ie j, com o valor 1 representando uma vitória ie 0 uma vitória j. Observe que T[i][j] == 1-T[j][i]se i != j. A diagonal de Tconsiste em 0s.

Sua saída será a lista de reis no torneio que Trepresenta, usando a indexação com base em 0 ou em 1. A ordem dos reis é irrelevante, mas não deve haver duplicatas.

Tanto a entrada como a saída podem ser obtidas em qualquer formato razoável.

Regras e pontuação

Você pode escrever um programa completo ou uma função. A contagem de bytes mais baixa vence e as brechas padrão não são permitidas.

Casos de teste

Esses casos de teste usam indexação baseada em 0. Para indexação baseada em 1, incremente cada valor de saída.

 2 [[0,0],[1,0]] -> [1]
 3 [[0,1,0],[0,0,0],[1,1,0]] -> [2]
 3 [[0,1,0],[0,0,1],[1,0,0]] -> [0,1,2]
 4 [[0,1,1,1],[0,0,1,0],[0,0,0,0],[0,1,1,0]] -> [0]
 4 [[0,1,1,0],[0,0,1,0],[0,0,0,1],[1,1,0,0]] -> [0,2,3]
 5 [[0,1,0,0,1],[0,0,0,0,1],[1,1,0,0,0],[1,1,1,0,1],[0,0,1,0,0]] -> [3]
 5 [[0,1,0,1,0],[0,0,1,1,1],[1,0,0,0,0],[0,0,1,0,1],[1,0,1,0,0]] -> [0,1,4]
 5 [[0,0,0,0,0],[1,0,1,1,0],[1,0,0,0,1],[1,0,1,0,1],[1,1,0,0,0]] -> [1,3,4]
 6 [[0,0,0,0,0,0],[1,0,1,1,0,0],[1,0,0,1,1,0],[1,0,0,0,1,1],[1,1,0,0,0,1],[1,1,1,0,0,0]] -> [1,2,3,4,5]
 6 [[0,0,1,1,1,0],[1,0,0,1,1,1],[0,1,0,0,1,0],[0,0,1,0,0,1],[0,0,0,1,0,1],[1,0,1,0,0,0]] -> [0,1,2,3,5]
 6 [[0,1,1,0,0,1],[0,0,0,1,0,1],[0,1,0,1,1,0],[1,0,0,0,1,1],[1,1,0,0,0,0],[0,0,1,0,1,0]] -> [0,1,2,3,4,5]
 8 [[0,0,1,1,0,1,1,1],[1,0,1,0,1,1,0,0],[0,0,0,1,1,0,0,0],[0,1,0,0,0,1,0,0],[1,0,0,1,0,1,0,0],[0,0,1,0,0,0,1,0],[0,1,1,1,1,0,0,1],[0,1,1,1,1,1,0,0]] -> [0,1,4,6,7]
20 [[0,0,1,1,0,1,1,0,0,0,0,1,1,0,1,1,1,1,0,1],[1,0,1,1,1,0,1,1,1,1,1,0,1,1,1,1,1,1,1,1],[0,0,0,1,0,0,0,1,1,0,1,0,1,0,0,0,0,0,1,1],[0,0,0,0,1,1,1,1,1,1,1,1,0,0,1,0,0,1,1,1],[1,0,1,0,0,0,0,1,1,0,1,1,1,0,1,1,1,1,0,1],[0,1,1,0,1,0,1,1,1,1,1,0,1,1,1,0,1,1,0,1],[0,0,1,0,1,0,0,1,1,0,1,0,1,1,1,1,1,0,1,0],[1,0,0,0,0,0,0,0,1,0,1,1,1,1,0,0,1,1,1,0],[1,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,0,1,1],[1,0,1,0,1,0,1,1,0,0,1,0,0,0,0,1,0,1,1,1],[1,0,0,0,0,0,0,0,0,0,0,1,1,1,0,1,0,0,0,0],[0,1,1,0,0,1,1,0,0,1,0,0,1,1,1,1,1,0,1,1],[0,0,0,1,0,0,0,0,0,1,0,0,0,0,1,1,0,1,1,1],[1,0,1,1,1,0,0,0,0,1,0,0,1,0,1,1,1,1,1,1],[0,0,1,0,0,0,0,1,0,1,1,0,0,0,0,1,1,0,0,1],[0,0,1,1,0,1,0,1,0,0,0,0,0,0,0,0,0,1,1,1],[0,0,1,1,0,0,0,0,0,1,1,0,1,0,0,1,0,0,1,1],[0,0,1,0,0,0,1,0,1,0,1,1,0,0,1,0,1,0,1,1],[1,0,0,0,1,1,0,0,0,0,1,0,0,0,1,0,0,0,0,0],[0,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,1,0]] -> [0,1,3,4,5,7,8,11,15,17,18]

(Existe algum tempo de execução ou limites de memória?) Não importa. Eu entendi completamente errado as especificações.
285 Dennis

@Dennis Nope. Desde que o seu programa funcione teoricamente, com tempo e memória ilimitados, você estará bem.
Zgarb 28/03

Apenas para esclarecer: T [a] [b] é a mesma que T [b] [a], mas vista de um ângulo oposto, então T [a] [b] ==! T [b] [a]
edc65

@ edc65 Essa é uma boa observação. Eu editei para o desafio.
Zgarb 28/03

Respostas:


9

Matlab, 36 35 29 bytes

@(T,N)find(sum(T*T>-T,2)>N-2)

Vamos descobrir se ié um rei. Então, para cada um, jo valor T[i][j]==1 OR there is a k such that T[i][k] * T[k][l] == 1. Mas a segunda condição também pode ser substituída por sum_over_k(T[i][k] * T[k][l])>0, mas essa é apenas uma entrada da matriz T*T(se você considerar Tuma matriz). O ORpode então ser repetido adicionando Ta esse resultado, portanto, apenas precisamos verificar se os n-1valores da linha ide T*T+Tsão maiores que zero, para ver se ié rei. É exatamente isso que minha função faz.

(Este é o MATLAB, portanto, os índices são baseados em 1).

As matrizes MATLAB devem ser codificadas com ponto e vírgula como delimitadores de linha:

[[0,0,0,0,0];[1,0,1,1,0];[1,0,0,0,1];[1,0,1,0,1];[1,1,0,0,0]] 

Provavelmente você pode salvar alguns bytes tomando o número de participantes como entrada, em vez de fazêsize(T,1)
Luis Mendo

7

Geléia, 13 12 11 bytes

a"€¹o/€oḅ1M

A saída é baseada em 1. Experimente online!

Como alternativa, usando operadores bit a bit em vez de manipulação de matriz:

×Ḅ|/€|ḄBS€M

Novamente, a saída é baseada em 1. Experimente online!

fundo

Para o competidor A , podemos encontrar todos B tal que uma batida C batida B , tomando todas as linhas que correspondem a um C tal que C bater um . IFR o B th entrada da C th é 1 , temos que C bater B .

Se computarmos os ORs lógicos de todas as entradas correspondentes das colunas selecionadas, obteremos um único vetor indicando se A vence B por transitividade ou não. Finalmente, ORing o vetor resultante com a linha correspondente da matriz de entrada fornece aos booleanos se A vence B , por transitividade ou diretamente.

Repetindo este para cada linha, contamos o número de 1 's em cada vetor, portanto, calcular a quantidade de concorrentes cada uma batida. A contagem máxima corresponde aos reis do torneio.

Como funciona

a"€¹o/€oḅ1M  Main link. Argument: M (matrix)

   ¹         Yield M.
  €          For each row of M:
a"           Take the logical AND of each entry of that row and the corr. row of M.
    o/€      Reduce each resulting matrix by logical OR.
       o     Take the logical OR of the entries of the resulting maxtrix and the
             corr. entries of M.
        ḅ1   Convert each row from base 1 to integer, i.e. sum its elements.
          M  Get all indices of maximal sums.
×Ḅ|/€|ḄBS€M  Main link. Argument: M (matrix)

 Ḅ           Convert each row of M from base 2 to integer. Result: R
×            Multiply the entries of each column of M by the corr. integer.
  |/€        Reduce each row fo the resulting matrix by bitwise OR.
     |Ḅ      Bitwise OR the results with R.
       BS€   Convert to binary and reduce by sum.
             This counts the number of set bits for each integer.
          M  Get all indices of maximal popcounts.

1
Você sabe, as pessoas continuam postando e dizendo x "bytes", mas "ḅ" é realmente codificado em 1 byte em qualquer codificação padrão? Desculpe, mas acho essas linguagens baseadas em pilha hipercondensadas completamente desinteressantes porque parece trapaça atribuir todas as funções concebíveis a um caractere unicode.
MattPutnam

2
O @MattPutnam Jelly usa sua própria codificação personalizada. (Também não é baseado em pilha)
um spaghetto

2
@MattPutnam Tive sentimentos semelhantes, mas eles não prejudicam o golfe tradicional. Ninguém menospreza os idiomas tradicionais apenas porque eles existem e, diferentemente de outros sites de SE, isso não tem exatamente a 'essa resposta é obvjectivamente melhor que a resposta'. Além disso, embora tecnicamente não sejam proibidos, eles não alteram o idioma para dar suporte a uma pergunta (embora possam, após o fato, perceber um atalho útil para perguntas futuras e tornar isso uma operação).
corsiKa

Por que esses algoritmos produzem os reis?
Xnor

@ Dennis vejo agora, sua multiplicação de matriz basicamente booleana feita via lógica ou aritmética de bits. A multiplicação real da matriz não seria mais curta?
xnor 28/03

2

Python usando numpy, 54 bytes

import numpy
lambda M:(M**0+M+M*M).all(1).nonzero()[0]

Recebe uma matriz numpy, gera uma matriz de linhas numpy de índices baseados em 0.

Outra maneira de pensar em um rei é como um competidor pelo qual todos os competidores estão na união do rei, as pessoas que o rei derrotou e as pessoas que essas pessoas vencem. Em outras palavras, para todo competidor, existe um caminho de no máximo 2 do rei para eles entre a relação "batida".

O Matrix I + M + M*M codifica o número de caminhos de 0, 1 ou 2 etapas de cada origem para cada destino. Um jogador é rei se a sua linha desta matriz tiver apenas entradas positivas. Como 0 é Falsey, allnos diz se uma linha é diferente de zero. Aplicamos isso a cada linha e produzimos os índices dos resultados diferentes de zero.


Parece exatamente como a minha abordagem, mas com uma interpretação differnt, = interessantes)
flawr

2

JavaScript (ES6), 83 bytes

a=>a.map((b,i)=>b.every((c,j)=>c|i==j|b.some((d,k)=>d&a[k][j]))&&r.push(i),r=[])&&r

Você pode salvar 1 com a => a.map ((b, i) => b.todos ((c, j) => c | i == j | b.some ((d, k) => d & a [ k] [j])) && i + 1) .filter (a => a) mas isso significa que você tem a saída 1-indexados, que é uma chatice grave
Charlie Wynn

2

MATL , 12 10 9 bytes

Xy+HY^!Af

A entrada é: primeiro o número de participantes e, em uma linha separada, uma matriz com linhas separadas por ponto e vírgula. A saída é baseada em 1.

Por exemplo, o quinto caso de teste tem entrada

4
[0,1,1,0; 0,0,1,0; 0,0,0,1; 1,1,0,0]

e o último caso de teste tem entrada

20
[0,0,1,1,0,1,1,0,0,0,0,1,1,0,1,1,1,1,0,1; 1,0,1,1,1,0,1,1,1,1,1,0,1,1,1,1,1,1,1,1; 0,0,0,1,0,0,0,1,1,0,1,0,1,0,0,0,0,0,1,1; 0,0,0,0,1,1,1,1,1,1,1,1,0,0,1,0,0,1,1,1; 1,0,1,0,0,0,0,1,1,0,1,1,1,0,1,1,1,1,0,1; 0,1,1,0,1,0,1,1,1,1,1,0,1,1,1,0,1,1,0,1; 0,0,1,0,1,0,0,1,1,0,1,0,1,1,1,1,1,0,1,0; 1,0,0,0,0,0,0,0,1,0,1,1,1,1,0,0,1,1,1,0; 1,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,0,1,1; 1,0,1,0,1,0,1,1,0,0,1,0,0,0,0,1,0,1,1,1; 1,0,0,0,0,0,0,0,0,0,0,1,1,1,0,1,0,0,0,0; 0,1,1,0,0,1,1,0,0,1,0,0,1,1,1,1,1,0,1,1; 0,0,0,1,0,0,0,0,0,1,0,0,0,0,1,1,0,1,1,1; 1,0,1,1,1,0,0,0,0,1,0,0,1,0,1,1,1,1,1,1; 0,0,1,0,0,0,0,1,0,1,1,0,0,0,0,1,1,0,0,1; 0,0,1,1,0,1,0,1,0,0,0,0,0,0,0,0,0,1,1,1; 0,0,1,1,0,0,0,0,0,1,1,0,1,0,0,1,0,0,1,1; 0,0,1,0,0,0,1,0,1,0,1,1,0,0,1,0,1,0,1,1; 1,0,0,0,1,1,0,0,0,0,1,0,0,0,1,0,0,0,0,0; 0,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,1,0]

Experimente online!

Explicação

Xy    % Implicitly take input: number. Push identity matrix with that size
+     % Implicitly take input: matrix. Add to identity matrix
HY^   % Matrix square
!     % Transpose
A     % Row vector with true entries for columns that contain all nonzero values
f     % Indices of nonzero values

1
MATL <Jelly \ m /
flawr

1

Javascript 136 131 121 112 bytes

(n,m)=>m.map((a,k)=>eval(a.map((o,i)=>o||eval(a.map((p,j)=>p&&m[j][i]).join`|`)).join`+`)>n-2&&k+1).filter(a=>a)

Ligue usando:

f=(n,m)=>m.map((a,k)=>eval(a.map((o,i)=>o||eval(a.map((p,j)=>p&&m[j][i]).join`|`)).join`+`)>n-2&&k+1).filter(a=>a)

f(20,[[0,0,1,1,0,1,1,0,0,0,0,1,1,0,1,1,1,1,0,1],
     [1,0,1,1,1,0,1,1,1,1,1,0,1,1,1,1,1,1,1,1],
     [0,0,0,1,0,0,0,1,1,0,1,0,1,0,0,0,0,0,1,1],         
     [0,0,0,0,1,1,1,1,1,1,1,1,0,0,1,0,0,1,1,1],
     [1,0,1,0,0,0,0,1,1,0,1,1,1,0,1,1,1,1,0,1],         
     [0,1,1,0,1,0,1,1,1,1,1,0,1,1,1,0,1,1,0,1],
     [0,0,1,0,1,0,0,1,1,0,1,0,1,1,1,1,1,0,1,0],         
     [1,0,0,0,0,0,0,0,1,0,1,1,1,1,0,0,1,1,1,0],
     [1,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,0,1,1],         
     [1,0,1,0,1,0,1,1,0,0,1,0,0,0,0,1,0,1,1,1],
     [1,0,0,0,0,0,0,0,0,0,0,1,1,1,0,1,0,0,0,0],         
     [0,1,1,0,0,1,1,0,0,1,0,0,1,1,1,1,1,0,1,1],
     [0,0,0,1,0,0,0,0,0,1,0,0,0,0,1,1,0,1,1,1],         
     [1,0,1,1,1,0,0,0,0,1,0,0,1,0,1,1,1,1,1,1],
     [0,0,1,0,0,0,0,1,0,1,1,0,0,0,0,1,1,0,0,1],         
     [0,0,1,1,0,1,0,1,0,0,0,0,0,0,0,0,0,1,1,1],
     [0,0,1,1,0,0,0,0,0,1,1,0,1,0,0,1,0,0,1,1],         
     [0,0,1,0,0,0,1,0,1,0,1,1,0,0,1,0,1,0,1,1],
     [1,0,0,0,1,1,0,0,0,0,1,0,0,0,1,0,0,0,0,0],             
     [0,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,1,0]])

watchout porque a saída é indexada em 1 (salvou alguns bytes sem tentar filtrar 0s e falsas)

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.