Gere a tabela de grupo para Z_n

9

Os grupos são uma estrutura amplamente utilizada em matemática e têm aplicações em ciência da computação. Esse desafio de código é sobre o menor número de caracteres para criar uma tabela de grupo para o grupo de aditivos Z n .

Como a tabela é construída: Para Z n , os elementos são {0, 1, 2, ..., n-1}. A tabela terá n linhas e n colunas. Para a i-ésima entrada da tabela, o valor é i + j mod n. Por exemplo, em Z 3 , a 1-2ª entrada (2ª linha, 3ª coluna se você contar a linha / coluna inicial como 1) é (1 + 2)% 3 = 0 (consulte a saída de amostra).

Entrada: um número inteiro positivo, n

Saída: uma tabela que é uma apresentação textual de Z n , construída como descrito acima, e exibida como mostrado abaixo nas saídas de amostra. Os espaços são opcionais

Entrada de amostra: 3

Saída de amostra:

0 1 2
1 2 0
2 0 1

Entrada de amostra: 5

Saída de amostra:

0 1 2 3 4
1 2 3 4 0
2 3 4 0 1
3 4 0 1 2
4 0 1 2 3
Ryan
fonte
3
Como o separador é opcional, haverá uma entrada acima de 10?
Jo rei
@JoKing baseado em codegolf.stackexchange.com/questions/35038/... Eu acho que sim
QWR

Respostas:

10

APL (10)

(Supondo ⎕IO=0. Funciona em ngn / apl por padrão, outros APLs tendem a precisar de um ⎕IO←0primeiro.)

{⍵|∘.+⍨⍳⍵}

Explicação:

  • ⍳⍵: os números [0..⍵)
  • ∘.+⍨: criar uma tabela de soma
  • ⍵|: números na tabela mod
marinus
fonte
11
Você pode fazer ⊢|⍳∘.+⍳ou os trens não funcionaram na versão de julho de 2014 da ngn?
lirtosiast
3

GolfScript (13 caracteres)

Pelo seu comentário sobre a resposta de Claudiu, entendo que não é necessário espaço em branco entre os elementos de uma linha. Sobre esse entendimento:

~.,{.n\(+}@(*

Demonstração online

Dissecação:

~        Parse the input into an integer
.,       Duplicate it, turn the second into an array [0,...,n-1]
{        Loop: top of stack is the previous row
  .n\    Push a newline and a copy of the previous row
  (+     Rotate the first element to the end to get the new row
}@(*     Perform loop n-1 times

Se for necessário espaço em branco, por 20 caracteres:

~.,{.(+}@(*]{' '*n}/
Peter Taylor
fonte
Trabalho muito bom sobre estes!
Ryan
3

Python 2, 66 bytes

def f(n):R=range(n);exec"print''.join(map(str,R));R+=R.pop(0),;"*n

Gira a lista popeando e anexando novamente.

Python 3, 53 bytes

def f(n):*R,=range(n);[print(*R[i:]+R[:i])for i in R]

Usa o mesmo método que @ mbomb007, mas abusando printcomo uma função.

Sp3000
fonte
Essa *R,=é uma construção estranha ... Serve apenas para converter rangea saída em uma tupla?
Jonathan Frech
Você pode explicar o código Python 3, por favor? Eu não vi o uso de*R
tarit goswami 16/09/18
@taritgoswami É degenerado desembalando; rangeé um objeto iterável que pode ser descompactado e reembalado, coletando tudo R. Deve ser equivalente R=list(range(n)), sendo o primeiro mais conciso.
Jonathan Frech
3

05AB1E , 10 8 bytes

ݨDδ+I%»

Experimente online!

Explicação

         # Implicit input n = 3                  [3]
Ý        # Push range(0,3)                       [[0,1,2,3]]
 ¨       # Pop last element                      [[0,1,2]]
  D      # Duplicate                             [[0,1,2],[0,1,2]]
   δ     # Apply next operation double vectorized
    +    # Vectorized addition                   [[[0,1,2],[1,2,3],[2,3,4]]]
     I   # Push input                            [[[0,1,2],[1,2,3],[2,3,4]],3]
      %  # Elementwise modulo 3                  [[[0,1,2],[1,2,0],[2,0,1]]]
       » # " ".join(x) followed by newline       ["0 1 2\n1 2 0\n2 0 1\n"]
           for every x in list       

Resposta anterior: 10 bytes

ݨDvDðý,À}

Experimente online!

Minha primeira tentativa no golfe em 05AB1E.

Explicação da resposta anterior

           # Implicit input n = 3                   [3]
Ý          # Push range(0,3)                        [[0,1,2,3]]
 ¨         # Pop last element.                      [[0,1,2]]
  D        # Duplicate                              [[0,1,2],[0,1,2]]
   v     } # Pop list and loop through elements     [[0,1,2]]
    D      # Duplicate                              [[0,1,2],[0,1,2]]
     ð     # Push space char                        [[0,1,2],[0,1,2], " "]
      ý    # Pop list a and push string a.join(" ") [[0,1,2],"0 1 2"]
       ,   # Print string with trailing newline     [[0,1,2]] Print: "0 1 2"
        À  # Rotate list                            [[1,2,0]]  
Wisław
fonte
11
Boa primeira resposta, e bem-vindo! Acho que pode ser mais curto, mas aqui estão duas alternativas de 9 bytes: FݨN._ðý,e fiqueݨsGDÀ})» à vontade para fazer qualquer pergunta no bate-papo 05AB1E e dê uma olhada na página de dicas do 05AB1E, se você ainda não o fez. :)
Kevin Cruijssen 14/01/19
@KevinCruijssen Thanks! Parece que eu esqueci de encontrar uma maneira de tirar proveito da entrada implícita.
Wisław 14/01/19
1

Pyth , 16

JVQXQjdJ=J+tJ]hJ

Imprime a tabela com espaço em branco apropriado.

./pyth.py -c "JVQXQjdJ=J+tJ]hJ" <<< 5
0 1 2 3 4
1 2 3 4 0
2 3 4 0 1
3 4 0 1 2
4 0 1 2 3

Explicação:

                   Automatic: Q=eval(input())
JVQ                J = range(Q)
XQ                 repeat Q times
  jdJ              print J, joined on " "
  =J               J =
    +tJ]hJ             tail(J) + [head(J)] (J[1:] + [J[-1]]])
isaacg
fonte
1

J, 20

Lendo de stdin e produzindo uma matriz 2D (que renderiza o mesmo que a amostra na pergunta).

(|+/~@i.)@".}:1!:1]3

Se uma função usando uma string for suficiente (|+/~@i.)@".,. Se uma função que aceita um número inteiro for suficiente, |+/~@i.deve ser suficiente.

Explicação: f g em J (para as funções f, g) denota um "gancho", que é uma função composta que executa a entrada através de g (uma função unária) e depois a entrada e o resultado de g através de f (uma função binária). A resposta é um garfo com componentes |(módulo) e +/~@i.. A última parte é "tabela de somas composta com lista de índices até" ( i.é um pouco como rangeem Python).

FireFly
fonte
Você deve atualizar sua resposta |+/~@i., o que deve ser aceitável pelas regras padrão aqui.
Jonah
1

Oitava, 23

@(n)mod((r=0:n-1)'+r,n)
alefalpha
fonte
1

Python 2, 67

Experimente os dois aqui

Eu uso a divisão de lista para "girar" os ntempos da lista , imprimindo-a sempre. (68 caracteres)

def f(n):
 l=range(n)
 for i in l:print''.join(map(str,l[i:]+l[:i]))

Consegui conseguir um personagem mais curto que o anterior com um truque estranho. (67 caracteres)

def f(n):
 l=range(n)
 for i in l:print''.join(`l[i:]+l[:i]`)[1::3]
mbomb007
fonte
Parece que este método é ainda mais curto em Python 3: def f(n):*R,=range(n);[print(*R[i:]+R[:i])for i in R]. Eu não acho que o splat realmente funcionaria sem parênteses.
Sp3000
1

Matlab (28)

k=exp(0:n-1)
mod(log(k'*k),n)
flawr
fonte
1

x86-64 Código da Máquina (Linux), 80 64 bytes

0000000000000000 <zn_asm>:
   0:   6a 0a                   pushq  $0xa
   2:   89 f9                   mov    %edi,%ecx
   4:   ff c9                   dec    %ecx

0000000000000006 <zn_asm.l1>:
   6:   c6 06 0a                movb   $0xa,(%rsi)
   9:   48 ff ce                dec    %rsi
   c:   89 fb                   mov    %edi,%ebx
   e:   ff cb                   dec    %ebx

0000000000000010 <zn_asm.l2>:
  10:   89 c8                   mov    %ecx,%eax
  12:   01 d8                   add    %ebx,%eax
  14:   31 d2                   xor    %edx,%edx
  16:   f7 f7                   div    %edi
  18:   89 d0                   mov    %edx,%eax

000000000000001a <zn_asm.l3>:
  1a:   31 d2                   xor    %edx,%edx
  1c:   48 f7 34 24             divq   (%rsp)
  20:   83 c2 30                add    $0x30,%edx
  23:   88 16                   mov    %dl,(%rsi)
  25:   48 ff ce                dec    %rsi
  28:   85 c0                   test   %eax,%eax
  2a:   75 ee                   jne    1a <zn_asm.l3>
  2c:   ff cb                   dec    %ebx
  2e:   85 db                   test   %ebx,%ebx
  30:   7d de                   jge    10 <zn_asm.l2>
  32:   ff c9                   dec    %ecx
  34:   85 c9                   test   %ecx,%ecx
  36:   7d ce                   jge    6 <zn_asm.l1>
  38:   58                      pop    %rax
  39:   48 89 f0                mov    %rsi,%rax
  3c:   48 ff c0                inc    %rax
  3f:   c3                      retq

Eu esperava que essa solução fosse apenas alguns bytes mais curta para poder superar alguns dos outros envios neste post. Existe a possibilidade de, se eu usar algumas das versões de 32 ou 16 bits dos registradores, poder cortar alguns bytes. A conversão de muitos registros para as versões de endereçamento de 32 bits economizou 16 bytes.

Basicamente, essa função é chamada de um programa C / C ++ que passou n por rdi e um ponteiro para uma alocação por rsi. O ponteiro que o rsi possui é na verdade 1 byte do final da alocação, já que a tabela é construída ao contrário. Isso facilita a conversão de um número inteiro para caracteres ASCII imprimíveis (feito com o número x mod 10 e a conversão do resultado em ASII).

Para ver o código do wrapper C ++ e comentários sobre o assembly, confira meu repositório .

davey
fonte
1

Pari / GP , 26 bytes

n->matrix(n,n,x,y,x+y-2)%n

Experimente online!

alefalpha
fonte
Quem inicializou x, y para quê?
RosLuP
@RosLuP matrix(m,n,X,Y,expr)gera uma mXnmatriz de expressão expr, a variável de linha Xpassando de 1para me a variável de coluna Yindo de 1para n.
Alephalpha
1

MathGolf , 10 8 bytes

r░y\Åo╫;

Experimente online!

-2 bytes graças a Jo King

Explicação

Vou usar exemplo de entrada 3para a explicação

r          range(0, n) ([0, 1, 2])
 ░         convert to string (implicit map) (['0', '1', '2'])
  y        join array without separator to string or number ('012')
   \       swap top elements ('012', 3)
    Å      start block of length 2 (for-loop, loops 3 times ('012'))
     o     print TOS without popping
      ╫    left-rotate bits in int, list/str ('012' => '120' => '201' => '012')
       ;   discard TOS (prevents final print)

Você também pode fazer r░y\(Åo╫, o que diminui o número de loops em 1 e ignora o descarte após o loop.

maxb
fonte
9 bytes
Jo King
@JoKing isso é inteligente! Talvez você possa usar qpara remover a duplicação?
maxb 12/01/19
Eu quis dizer o. Embora o melhor que eu pudesse descobrir dessa maneira fosse esse . Também pode ter 10 bytes, mas estou no celular.
Maxb 12/01/19
Como o separador é opcional, 8 bytes devem funcionar
Jo King
0

C - 96

void g(int k){int i;for(i=0;i<k*k;i++){if(i&&!(i%k))puts("\n");printf("%i ",((i/k)+(i%k))%k);}}
LemonBoy
fonte
0

Golfscript, 20 caracteres

Um trabalho terrivelmente preguiçoso.

~:j,{:x;j,{x+j%}%n}/

Execute aqui . (A primeira linha é simular stdin).

Explicação :

~                     # evaluate input (turn string "5" into number 5)
:j                    # store into variable j
,                     # turn top of stack into range(top), e.g. 5 --> [0, 1, 2, 3, 4]
{...}/                # for each element in the array... 
  :x;                 # store the element into x and pop from the stack
  j,                  # put range(j) on the stack ([0, 1, 2, 3, 4] again)
  {...}%              # map the array with the following:
      x+j%            # add x and mod the resulting sum by j
  n                   # put a newline on the stack

Quando o programa termina, a pilha contém cada uma das matrizes com novas linhas entre elas. O intérprete gera o que resta na pilha, fornecendo o resultado desejado.

Claudiu
fonte
11
Agradável! Embora os espaços entre os elementos não sejam necessários, pode ser útil quando tivermos elementos de valor> = 10 (ou seja, quando n> = 11).
24714 Ryan
Você pode exlain seu código? Para mim, ler golfscript é pior do que ler a expressão regular de outra pessoa. (quase =)
flawr
@flawr: Ah, claro, é bem direto #
Claudiu
0

CJam, 14 caracteres

l~_)_@,*/Wf<N*

Teste aqui.

Explicação

A idéia é repetir a string de 0para N-1, mas dividi-la em blocos de N+1. Essa incompatibilidade desloca a linha para a esquerda a cada vez. Por fim, precisamos nos livrar do caráter estranho e juntar tudo com novas linhas.

Aqui está o código explodido, junto com o conteúdo da pilha para entrada 3.

l~              "Read and eval input."; [3]
  _             "Duplicate.";           [3 3]
   )            "Increment.";           [3 4]
    _           "Duplicate.";           [3 4 4]
     @          "Rotate.";              [4 4 3]
      ,         "Get range.";           [4 4 [0 1 2]]
       *        "Repeat.";              [4 [0 1 2 0 1 2 0 1 2 0 1 2]
        /       "Split.";               [[[0 1 2 0] [1 2 0 1] [2 0 1 2]]
         Wf<    "Truncate each line.";  [[[0 1 2] [1 2 0] [2 0 1]]
            N*  "Join with newlines.";  ["012
                                          120
                                          201"]

O resultado é impresso automaticamente no final do programa. (Observe que o conteúdo da pilha para a etapa final é tecnicamente uma matriz mista contendo números e caracteres de nova linha, não uma sequência contendo apenas caracteres.)

Como alternativa, 11 caracteres

Com a adição recente ew(isso é mais recente que o desafio - ele retorna todas as substrings sobrepostas de determinado comprimento), pode-se fazer 11 bytes:

l~,2*))ewN*

Aqui está como este funciona:

l~           "Read and eval input."; [3]
  ,          "Get range.";           [[0 1 2]]
   2*        "Repeat twice.";        [[0 1 2 0 1 2]]
     )       "Pop last.";            [[0 1 2 0 1] 2]
      )      "Increment.";           [[0 1 2 0 1] 3]
       ew    "Get substrings.";      [[[0 1 2] [1 2 0] [2 0 1]]
         N*  "Join with newlines.";  ["012
                                       120
                                       201"]
Martin Ender
fonte
Alternativa 14 bytes: l~_,\{_(+N\}*;. Gostaria de saber se podemos fazer melhor com isso embora.
SP3000
Sim, mas isso é essencialmente um porto da resposta de Peter, e achei que preferiria apresentar uma abordagem diferente. ewpode funcionar, mas é mais recente que o desafio.
Martin Ender
0

MATL , 6 bytes

:q&+G\

Experimente online!

    # implicit input, say n = 3
:   # range
    # stack: [1, 2, 3]
q   # decrement
    # stack: [0, 1, 2]
&+  # sum with itself and transpose with broadcast
    # stack:
    # [0 1 2
    #  1 2 3
    #  2 3 4]
G   # paste input
    # stack: [0 1 2; 1 2 3; 2 3 4], 3
\   # elementwise modulo
    # implicit output with spaces
Giuseppe
fonte
0

Excel VBA, 77 bytes

Função de janela imediata VBE anônima que leva a entrada, como inteiro, n, do intervalo [A1]e as saídas para o intervalo A2.Resize(n,n).

[A2:IU255]="=IF(MAX(ROW()-1,COLUMN())-1<$A$1,MOD(ROW()+COLUMN()-3,$A$1),"""")
Taylor Scott
fonte
0

Perl 6 , 23 bytes

{.rotate(.all).put}o|^*

Experimente online!

Bloco de código anônimo que pega um número e imprime a matriz no formato especificado com espaços. Se pudermos retornar alguma coisa, ela .putpoderá ser removida.

Explicação:

                   o|^*    # Transform the input into the range 0..input-1
{                 }        # And pass it into the function
 .rotate                   # Rotate the range by
        (.all)             # Each of the range
              .put         # And print each of them separated by spaces
Brincadeira
fonte
0

Carvão vegetal , 13 bytes

NθEθ⪫Eθ﹪⁺ιλθ 

Experimente online! Link é a versão detalhada do código. Nota: Espaço à direita. Explicação:

Nθ              Input `n` as a number into variable
   θ            `n`
  E             Map over implicit range
      θ         `n`
     E          Map over implicit range
         ι      Current row
        ⁺       Plus
          λ     Current column
       ﹪        Modulo
           θ    `n`
    ⪫           Cast row to string and join with spaces
                Implicitly print each row on its own line
Neil
fonte
0

APL (NARS), 15 caracteres, 30 bytes

{⊃{⍵⌽k}¨k←0..⍵}

teste:

  f←{⊃{⍵⌽k}¨k←0..⍵}
  f 4
0 1 2 3 4
1 2 3 4 0
2 3 4 0 1
3 4 0 1 2
4 0 1 2 3
  f 3
0 1 2 3
1 2 3 0
2 3 0 1
3 0 1 2
  f 2
0 1 2
1 2 0
2 0 1
  f 1
0 1
1 0
  f 0
0 

aqui o idioma não precisa de comentários ...

RosLuP
fonte
0

Japt -R, 5 bytes

ÆZéXn

Tente

Se o uso de vírgula como separador não for válido, adicione um byte para nenhum separador:

ÆZ¬éXn

Tente

Ou 2 bytes para usar um espaço:

ÆZéXn)¸

Tente

Shaggy
fonte
0

R , 37 bytes

sapply(x<-1:scan()-1,`+`,x)%%sum(x|1)

Cria um vetor de 0 a n-1 e adiciona sequencialmente 1, depois 2 ... então n, e modula a matriz pelo comprimento do vetor, que é n.

Experimente online!

Sumner18
fonte
0

Quarto (gforth) , 53 bytes

: f dup 0 do cr dup 0 do i j + over mod . loop loop ;

Experimente online!

Explicação

Loop aninhado que gera uma nova linha a cada n números

Código Explicação

: f             \ start new word definition
  dup 0 do      \ set loop parameters and loop from 0 to n-1
    cr          \ output a newline
    dup 0 do    \ loop from 0 to n-1 again
      i j +     \ get the sum of the row and column number
      over mod  \ modulo with n
      .         \ print (with space)
    loop        \ end inner loop
  loop          \ end outer loop
;               \ end word definition
reffu
fonte