Fizz Buzz para tartarugas

35

Descrição do Problema

Imagine que você é uma tartaruga em uma grade. Você é dado dois números f e b , e você está voltada para o leste. Você realiza uma marcha pela grade, contando cada uma das células que encontrar, de acordo com as seguintes regras:

  • Por padrão, você escreve a contagem na célula em que está e depois avança.
  • Se a contagem é divisível por f , você escreve Fna célula em que está, depois vira à direita e depois avança.
  • Se a contagem é divisível por b , você escreve Bna célula em que está, depois vira à esquerda e depois avança.
  • Se a contagem é divisível por f e b , você escreve FBna célula em que está e depois avança.
  • Se você chegar a um quadrado em que já esteve, pare.

Por exemplo, seguir estas regras usando f = 3 eb = 5 gerará um padrão como este:

    F 28 29 FB  1  2  F
   26                 4
 F  B                 B  F
23                       7
22                       8
 F  B                 B  F
   19                11
    F 17 16 FB 14 13  F

O desafio

Escrever um programa ou função que aceita dois números como entrada, correspondendo a f e b , e produz como saída o padrão para esses números indicados pelas regras acima.

Requisitos de formatação:

  • Cada célula tem dois caracteres de largura
  • O conteúdo da célula está alinhado à direita dentro desses dois caracteres
  • As células na mesma linha são delimitadas por um espaço
  • A primeira coluna de células deve conter uma célula não vazia
  • Todas as linhas devem conter células não vazias
  • O espaço em branco à direita não é necessário, mas é permitido
  • No entanto, a largura total de cada linha não deve exceder 3 vezes o número de colunas não vazias

Seu código deve funcionar para os casos de teste fornecidos.

As brechas padrão não são permitidas.

Isso é código de golfe; a resposta mais curta em bytes vence.

Casos de teste

(f = 3, b = 5 caso repetido aqui como uma conveniência de cortesia).

f=3, b=5 ->
    F 28 29 FB  1  2  F
   26                 4
 F  B                 B  F
23                       7
22                       8
 F  B                 B  F
   19                11
    F 17 16 FB 14 13  F

f=4, b=10 ->
 F 25 26 27  F
23          29
22        1  2  3  F
21                 5
FB                 6
19                 7
18           B  9  F
17          11
 F 15 14 13  F

f=3, b=11 ->
 F 16 17  F
14       19
13     1  2  F
 F  B        4
   10        5
    F  8  7  F

f=5, b=9 ->
    F 41 42 43 44  1  2  3  4  F
   39                          6
   38                          7
   37                          8
 F  B                          B  F
34                               11
33                               12
32                               13
31                               14
 F 29 28  B              B 17 16  F
         26             19
          F 24 23 22 21  F

f=5, b=13 ->
    F 31 32 33 34  F
   29             36
   28        1  2  3  4  F
   27                    6
 F  B                    7
24                       8
23                       9
22              B 12 11  F
21             14
 F 19 18 17 16  F
H Walters
fonte
11
Temos a garantia de que a entrada sempre levará a uma colisão antes de chegarmos a 100?
Martin Ender
Sim. De maneira mais geral, desde que seu código funcione para os casos de teste fornecidos, você estará pronto.
H Walters
11
Existe um lugar específico em que você (a tartaruga) começa?
Kritixi Lithos 7/11
@KritixiLithos Não. A esquerda / parte superior / direita / parte inferior da grade são definidas pela forma como a tartaruga viaja, o que depende de f e b.
perfil completo de H Walters
F e b são sempre inteiros?
corvus_192

Respostas:

1

JavaScript (ES6), 230 240

(f,b)=>(d=>{for(g=[s=x=y=d];!(r=g[y]=g[y]||[])[x];d&1?d&2?y?--y:g=[,...g]:++y:d&2?x?--x:g=g.map(r=>[,...r]):++x)o=++s%f?'':(++d,'F'),s%b||(--d,o+='B'),r[x]=o||s})(0)||g.map(r=>[...r].map(c=>` ${c||' '}`.slice(-2)).join` `).join`
`

Menos golfe

(f,b)=>{
  for(g=[s=x=y=d=0]; !(r = g[y]= g[y]||[])[x]; )
  {
    o=++s%f?'':(++d,'F')
    s%b||(--d,o+='B')
    r[x]=o||s,
    d&1
      ? d&2 ? y ? --y : g=[,...g] : ++y
      : d&2 ? x ? --x : g=g.map(r=>[,...r]) : ++x
  }
  return g.map(r=>[...r].map(c=>` ${c||' '}`.slice(-2)).join` `)
          .join`\n`
}

Teste

F=
(f,b)=>(d=>{for(g=[s=x=y=d];!(r=g[y]=g[y]||[])[x];d&1?d&2?y?--y:g=[,...g]:++y:d&2?x?--x:g=g.map(r=>[,...r]):++x)o=++s%f?'':(++d,'F'),s%b||(--d,o+='B'),r[x]=o||s})(0)||g.map(r=>[...r].map(c=>` ${c||' '}`.slice(-2)).join` `).join`
`


function update()
{
  var i = I.value.match(/\d+/g)||[],f=+i[0],b=+i[1]
  O.textContent = (f>0 & b>0) ? F(f,b) : ''
}  

update()
<input id=I value="3 5" oninput="update()">
<pre id=O></pre>

edc65
fonte
5

Python 2, 379 338 326 bytes

Recebe a entrada como dois números, separados por vírgula. Por exemplo. 4,5ou(4,5)

d=x=y=i=q=Q=e=E=0
p={}
f,b=input()
while(x,y)not in p:
 i+=1;l,r=i%b<1,i%f<1;d=(d+r-l)%4;p[x,y]=[[`i`,'F'][r],' F'[r]+'B'][l].rjust(2);q=min(q,x);Q=max(Q,x);e=min(e,y);E=max(E,y)
 if d%2:x+=(d==1)*2-1
 else:y+=(d!=2)*2-1
h,w=E-e+1,Q-q+1
A=[h*['  ']for x in' '*w]
for x,y in p:A[x-q][y-e]=p[x,y]
print'\n'.join(map(' '.join,A))

Versão que funciona se o caminho for maior que 99, 384 343 330 bytes

Mostra 2 dígitos significativos.

d=x=y=i=q=Q=e=E=0
p={}
f,b=input()
while(x,y)not in p:
 i+=1;l,r=i%b<1,i%f<1;d=(d+r-l)%4;p[x,y]=[[`i%100`,'F'][r],' F'[r]+'B'][l].rjust(2);q=min(q,x);Q=max(Q,x);e=min(e,y);E=max(E,y)
 if d%2:x+=(d==1)*2-1
 else:y+=(d!=2)*2-1
h,w=E-e+1,Q-q+1
A=[h*['  ']for x in' '*w]
for x,y in p:A[x-q][y-e]=p[x,y]
print'\n'.join(map(' '.join,A))

Exemplos:

input=(4,16)

 F 21 22 23  F
19          25
18          26
17          27
FB  1  2  3  F
15           5
14           6
13           7
 F 11 10  9  F

input=(6,7) (versão truncada)

                                              F 63 64 65 66 67 FB  1  2  3  4  5  F                                             
                               F 57 58 59 60  B                                   B  8  9 10 11  F                              
                              55                                                                13                              
                   F 51 52 53  B                                                                 B 15 16 17  F                  
                  49                                                                                        19                  
                  48                                                                                        20                  
          F 45 46  B                                                                                         B 22 23  F         
         43                                                                                                          25         
         42                                                                                                          26         
         41                                                                                                          27         
    F 39  B                                                                                                           B 29  F   
   37                                                                                                                      31   
   36                                                                                                                      32   
   35                                                                                                                      33   
   34                                                                                                                      34   
 F  B                                                                                                                       B  F
31                                                                                                                            37
30                                                                                                                            38
29                                                                                                                            39
28                                                                                                                            40
27                                                                                                                            41
FB                                                                                                                            FB
25                                                                                                                            43
24                                                                                                                            44
23                                                                                                                            45
22                                                                                                                            46
21                                                                                                                            47
 F  B                                                                                                                       B  F
   18                                                                                                                      50   
   17                                                                                                                      51   
   16                                                                                                                      52   
   15                                                                                                                      53   
    F 13  B                                                                                                           B 55  F   
         11                                                                                                          57         
         10                                                                                                          58         
         09                                                                                                          59         
          F 07 06  B                                                                                         B 62 61  F         
                  04                                                                                        64                  
                  03                                                                                        65                  
                   F 01 00 99  B                                                                 B 69 68 67  F                  
                              97                                                                71                              
                               F 95 94 93 92  B                                   B 76 75 74 73  F                              
                                              F 89 88 87 86 85 FB 83 82 81 80 79  F                                             

@ Edit: Obrigado a Jonathan Allan, Copper e shooqie por me poupar um monte de bytes.

TFeld
fonte
Heh, esses padrões N, 4N são bem legais.
steenbergh
Bom trabalho. Você pode mudar while((x,y)not in p.keys()):para while(x,y)not in p:e for x,y in p.keys():para for x,y in p. Você pode mudar l,r=i%b==0,i%f==0para l,r=i%b<1,i%f<1e d=(d+[0,1][r]-[0,1][l])%4para d=(d+r-l)%4. Você pode mudar s=[[`i`,'F'][r],' F'[r]+'B'][l].rjust(2);p[(x,y)]=spara p[(x,y)]=[[`i`,'F'][r],' F'[r]+'B'][l].rjust(2). Pode haver mais
Jonathan Allan
Você pode salvar um byte em h*[' ']for x in rangevez de [' ']*h for x in range. Além disso, x+=[-1,1][d==1]pode ser substituído por x+=(d==1)*2-1e y+=[1,-1][d==2]pode ser substituído por y+=(d!=2)*2-1. Além disso, é f,b=inputttum erro de digitação?
Cobre
p[(x,y)]=> p[x,y](Não tenho certeza se ele funciona em Python 2, embora)
shooqie
4

Excel VBA, 347 421 bytes

Nova versão, para lidar com os requisitos de espaço em branco. Não ter isso na minha primeira versão foi um descuido da minha parte, mas isso tem seu preço no número de bytes ... Agora, ele corta e cola o intervalo usado na célula A1.

Sub t(f, b)
x=70:y=70:Do:s=s+ 1
If Cells(y,x).Value<>"" Then
ActiveSheet.UsedRange.Select:Selection.Cut:Range("A1").Select:ActiveSheet.Paste:Exit Sub
End If
If s Mod f=0 Then Cells(y,x).Value="F":q=q+1
If s Mod b=0 Then Cells(y,x).Value=Cells(y,x).Value & "B":q=q+3
If Cells(y,x).Value="" Then Cells(y,x).Value=s
Select Case q Mod 4
Case 0:x=x+1
Case 1:y=y+1
Case 2:x=x-1
Case 3:y=y-1
End Select:Loop:End Sub

Aqui está a versão antiga que não moveu o resultado final para A1

Sub t(f,b)
x=70:y=70:Do:s=s+1:if Cells(y,x).Value<>"" then exit sub
If s Mod f=0 Then
Cells(y,x).Value="F":q=q+1
End If
If s Mod b=0 Then
Cells(y,x).Value=Cells(y,x).Value & "B":q=q+3
End If
If Cells(y,x).Value="" Then Cells(y,x).Value=s
Select Case q mod 4
Case 0:x=x+1
Case 1:y=y+1
Case 2:x=x-1
Case 3:y=y-1
End Select:Loop:End Sub

Começa às 70, 70 (ou BR70 no Excel) e caminha ao redor. A função é chamada com os parâmetros fe bcomo:Call t(4, 16)

@ Neil me salvou um monte de bytes, obrigado!

steenbergh
fonte
11
Se você substituir q=q-1por q=q+3e Select Case qcom Select Case q Mod 4, poderá se livrar das duas instruções anteriores.
911 Neil
However, the total width of each row must not exceed 3 times the number of non-empty columnsEu acho que isso foi adicionado para evitar apenas configurar uma grande grade e começar um pouco a distância da fronteira
Karl Napf
11
@KarlNapf Fixed.
213166 # java #
3

Excel VBA, 284 278 277 261 259 255 254 253 251 bytes

Subrotina que toma como entrada valores, F, Be as saídas de células no Sheets(1)objecto (que é restrito para o Sheets(1)objecto para salvar 2 bytes)

Sub G(F,B)
Set A=Sheet1
R=99:C=R
Do
I=I+1
Y=Cells(R,C)
If Y<>""Then A.UsedRange.Cut:[A1].Select:A.Paste:End
If I Mod F=0Then Y="F":J=J+1
If I Mod B=0Then Y=Y+"B":J=J+3
Cells(R,C)=IIf(Y="",i,Y)
K=J Mod 4
If K Mod 2Then R=R-K+2 Else C=C+1-K
Loop
End Sub

Uso:

Call G(3, 4)
Taylor Scott
fonte
2

C, 349 bytes

Compila com o gcc (com muitos avisos)

#define z strcpy(G[x][y],
char G[99][99][3];d=3,x=49,y=49,i=1,q,s=99,t,u=99,v;F(f,b){for(;!*G[x][y];i++){q=(!(i%f))<<1|!(i%b);q==3&&z"FB");if(q==2)z"F"),d=(d+3)%4;if(q==1)z"B"),d=(d+1)%4;!q&&sprintf(G[x][y],"%d",i);if(d%2)x+=d-2;else y+=d-1;s=s>x?x:s;t=t<x?x:t;u=u>y?y:u;v=v<y?y:v;}for(y=u;y<=v;puts(""),y++)for(x=s;x<=t;x++)printf("%2s ",G[x][y]);}

Uma versão um pouco mais recuada:

#define z strcpy(G[x][y],
char G[99][99][3];
d=3,x=49,y=49,i=1,q,s=99,t,u=99,v;

F(f,b)
{
    for(;!*G[x][y];i++)
    {
        q=(!(i%f))<<1|!(i%b);
        q==3&&z"FB");
        if(q==2)z"F"),d=(d+3)%4;
        if(q==1)z"B"),d=(d+1)%4;
        !q&&sprintf(G[x][y],"%d",i);
        if(d%2)x+=d-2;else y+=d-1;
        s=s>x?x:s;t=t<x?x:t;u=u>y?y:u;v=v<y?y:v;
    }
    for(y=u;y<=v;puts(""),y++)for(x=s;x<=t;x++)printf("%2s ",G[x][y]);
}

Aqui está uma versão de 364 bytes que lida com números maiores que 100

#define g G[x][y]
#define z strcpy(g,
char G[99][99][9];d=3,x=49,y=49,i=1,q,s=99,t,u=99,v;F(f,b){for(;!*g;i++){q=(!(i%f))<<1|!(i%b);q==3&&z"FB");if(q==2)z" F"),d=(d+3)%4;if(q==1)z" B"),d=(d+1)%4;!q&&sprintf(G[x][y],"%2d",i);if(d%2)x+=d-2;else y+=d-1;s=s>x?x:s;t=t<x?x:t;u=u>y?y:u;v=v<y?y:v;}for(y=u;y<=v;puts(""),y++)for(x=s;x<=t;x++)printf("%2s ",g+strlen(g)-2);}
Jerry Jeremiah
fonte
1

Perl, 275 bytes

O recuo é fornecido para facilitar a leitura e não faz parte do código.

($f,$e)=@ARGV;
for($i=$x=1,$y=0;!$m{"$x,$y"};$i++){
    ($g,$m{"$x,$y"})=$i%$e&&$i%$f?($g,$i):$i%$f?($g+1,B):$i%$e?($g-1,F):($g,FB);
    ($g%=4)%2?($y+=$g-2):($x+=1-$g);
    ($a>$x?$a:$b<$x?$b:$x)=$x;
    ($c>$y?$c:$d<$y?$d:$y)=$y
}
for$k($c..$d){
    printf("%*s",1+length$i,$m{"$_,$k"})for$a..$b;
    say
}

Explicação:

O código funciona controlando um hash de todos os lugares em que a tartaruga esteve e o valor apropriado armazenado %m. Por exemplo: in 3 5, $m{0,2}contém 2e $m{1,-3}= 26. Ele continua dessa maneira até chegar a um local que já foi definido. Além disso, ele mantém o controle das fronteiras atuais do caminho da tartaruga, usando $a,$b,$c,$dcomo máximos e mínimos.

Quando chega a um local em que já esteve, imprime o caminho usando os limites, tudo preenchido com espaços.

Não há limite para o tamanho do caminho, nem o tamanho dos números.

Gabriel Benamy
fonte
1

PHP , 292 bytes

for($x=$y=$u=$l=0;!$q[$x][$y];$s="") {
    ++$i%$argv[1]?:$a-=1+$s="F";
    $i%$argv[2]?:$a+=1+$s.="B";
    $q[$x][$y]=$s?:$i;
    $z=[1,-2,-1,2][$a=($a+4)%4];
    $y+=$z%2;
    $x+=~-$z%2;
    $u>$y?$u=$y:$d>$y?:$d=$y;
    $l>$x?$l=$x:$r>$x?:$r=$x;
}
for(;$l++<=$r;print"\n")for($j=$u-1;$j++<=$d;)echo str_pad($q[$l-1][$j],3," ",0);

Experimente online!

Recuos são para maior clareza, não são contados.

Segue o mesmo algoritmo da resposta Perl. Rastreie onde a tartaruga esteve em uma matriz 2D $a, $u, $d, $l, $rrastreie onde a tartaruga está virada e rastreie os limites para impressão. str_padnos permite garantir que cada entrada tenha exatamente 3 espaços de largura para a formatação da impressão.

Por alguma razão que eu não consigo entender, o PHP não se importa de eu não inicializar metade das variáveis ​​para 0, mas estraga a formatação se eu não inicializar outras, mesmo que geralmente trate variáveis ​​não inicializadas como 0 quando elas são as primeiras usava. Daí a parte $x=$y=$u=$l=0.

Xanderhall
fonte
0

Python 2 , 267 262 258 249 245 243 bytes

f,b=input()
X=x=Y=y=i=p=0
g={}
S=sorted
while(p in g)<1:i+=1;g[p]='F'[i%f:]+'B'[i%b:]or`i`;p+=1j**(i/f-i/b);X,_,x=S([X,x,int(p.real)]);Y,_,y=S([Y,y,int(p.imag)])
j=Y
while j<=y:print' '.join(g.get(i+j*1j,'').rjust(2)for i in range(X,x+1));j+=1

Experimente online!

Arfie
fonte