Resolver Grid-Tangram

22

O Tangram é um quebra-cabeça de dissecação feito de sete formas: cinco triângulos de tamanhos diferentes, um paralelogramo e um quadrado. Dada uma forma, o objetivo é recriar a forma usando todas as peças e sem sobreposição. Obviamente, existem infinitas maneiras de organizar esse conjunto de peças no plano. Um subconjunto interessante é o

Tangrams de grade

Podemos desenhar o quadrado "padrão" do Tangram em um quadrado maior, subdividido por uma grade em 16 quadrados menores. Os tangramas de grade são apenas formas compostas das peças do tangram, de modo que todos os vértices das peças estão nos pontos da grade.

Esses são os tipos de quebra-cabeças do Tangram que queremos considerar neste desafio, pois provavelmente são mais fáceis de manusear do que os mais gerais.

Como observação lateral: os matemáticos chineses Chuan-Chin Hsiung e Fu Traing Wang provaram em 1942 que existem apenas 13 tangramas convexos. Eles primeiro mostraram que o problema pode ser reduzido a tangramas de grade e, em seguida, usaram alguns argumentos combinatórios e geométricos. Estes são todos esses 13:

Desafio

Dado um tangram de grade solucionável, produza uma dissecção do tangram de grade nas sete partes do tangram.

IO

Um tangram é dado como uma imagem em preto e branco (a forma é em preto, o fundo em branco), com os dois lados múltiplos de 50px. A grade tem uma largura de exatamente 50 px. As linhas de grade são paralelas aos lados da imagem.

EDIT: A imagem pode ser aceita como entrada e retornada como saída em qualquer formato de imagem rasterizada conveniente, como PNG, TIFF, PBM, etc.

A saída deve ter novamente o mesmo tamanho e a mesma forma, mas com cada peça uma cor diferente ou, alternativamente, com linhas brancas separando todas as peças. Vale ressaltar que o quadrilátero não retangular pode ser invertido.

Os pixels na borda das peças não precisam exatamente coincidir com o da forma, também se houver efeitos de alias ou outro efeito difuso, isso ainda está ok.

Exemplo de entrada e saída:

Exemplos:

Soluções possíveis:

flawr
fonte
o processamento de imagens é um obstáculo totalmente desnecessário nesse desafio. Eu acharia muito mais atraente se você apenas especificasse a entrada como uma pequena matriz binária.
Sparr
1
Como eu disse, isso foi discutido quando estava na caixa de areia. Mas duvido que adicione muitos bytes, pois a tarefa em si é muito mais difícil.
flawr
3
Eu fui uma das pessoas que recomendou que as entradas e saídas fossem do jeito que são, e fiz essa recomendação porque essa é, na minha opinião, a maneira mais natural e adequada para apresentar um desafio do Tangram. Qualquer forma de entrada / saída levaria um número significativo de bytes, então não acho que seja realmente um problema aqui.
El'endia Starman 13/09/16
1
Eu concordo com Elendia. O único problema da E / S gráfica é que ela pode limitar idiomas que não possuem recursos gráficos. Dito isto, PBM e PGM estão tão próximos da arte ASCII que não há nenhum problema real, se as pessoas estiverem cientes desses formatos. pt.wikipedia.org/wiki/Netpbm_format
Level River St
1
@LevelRiverSt Esse é um bom ponto, acho que seria totalmente aceitável usar esses formatos ou mesmo, por exemplo, uma matriz / string 2D de zeros e uns.
flawr

Respostas:

31

BBC BASIC, 570 514 490 bytes ASCII

Faça o download do intérprete em http://www.bbcbasic.co.uk/bbcwin/download.html

435 bytes tokenizados

O programa completo exibe uma entrada L.bmpna tela e a modifica para encontrar uma solução.

*DISPLAY L
t=PI/8q=FNa(1)
DEFFNa(n)IFn=7END
LOCALz,j,p,i,c,s,x,y,m,u,v
F.z=0TO99u=z MOD10*100v=z DIV10*100ORIGINu,v
F.j=0TO12S.4p=0F.i=j+3TOj+9S.2c=9*COS(i*t)s=9*SIN(i*t)p=p*4-(POINT(c,s)<>0)*2-(POINT(9*c,9*s)<>0)N.
m=n:IFn=5A.(43A.p)=0p=0m=7
IF(ASCM."??O|(C",n)-64A.p)=0THEN
F.i=-1TO0GCOL0,-i*n:c=99*COS(j*t)s=99*SIN(j*t)y=402/3^m MOD3-1MOVE-c-s*y,c*y-s:x=n<3MOVEc*x-s*x,s*x+c*x:x=2778/3^m MOD3-1y=5775/3^m MOD3-1PLOT85-32*(n MOD6>3),c*x-s*y,s*x+c*y:IFi q=FNa(n+1)ORIGINu,v
N.
ENDIF
N.N.=0

Explicação

Observe que no básico da BBC uma distância de 1 pixel = 2 unidades, a grade de 50x50 pixels se torna uma grade de 100x100.

Usamos uma função recursiva para colocar os 2 triângulos grandes, triângulo médio, quadrado e paralelogramo na forma. A forma anterior da lista é desenhada antes da próxima chamada recursiva. se uma chamada recursiva retornar sem encontrar uma solução, a forma anterior será substituída em preto e uma nova posição da forma anterior será tentada.

Depois que essas cinco formas são desenhadas, colocar os dois pequenos triângulos é apenas uma formalidade. É necessário desenhar um deles, no entanto, para distingui-los se eles compartilham uma vantagem comum. Nós colorimos apenas um dos dois pequenos triângulos. O outro é deixado em preto natural.

A colocação de cada forma é tentada em diferentes coordenadas x, y e em 4 rotações diferentes. Para testar se há espaço livre para desenhar uma forma, usamos o modelo abaixo, com ângulos de 45 graus. As rotações são feitas em torno dos *8 pixels testados e estão em 2 semicírculos dos raios 9 e 81 unidades e caem nas linhas radiantes em múltiplos ímpares de 22,5 graus para os eixos xe y.

Para um triângulo grande, todos os 8 espaços devem estar limpos. Para outras formas, apenas algumas das células devem estar limpas para que uma máscara seja aplicada.

+----+----   Shape             Mask HGFEDCBA Mask decimal 
|\ E/|\G /  
| \/F|H\/    1,2. Large triangle    11111111    -1
|C/\ | /     3. Med triangle        00001111    15
|/ D\|/      4. Square              00111100    60
+----*       5. Parallelogram       11101000   -24
|\ B/        6. Small triangle      00000011     3
|A\/         7. Parallogr reversed  00101011    43
| /          Note: reversed parallelogram is checked/drawn at recursion depth n=5
|/           with a special check, but the coordinates are encoded as m=7.  

Uma vez estabelecido que uma forma se encaixa, ela deve ser desenhada. Se é um triângulo com o qual é plotado PLOT 85, se é um paralelogramo, o número é 32 maior (observe que, para PLOTfins, consideramos um quadrado um paralelogramo especial). Nos dois casos, três vértices consecutivos devem ser dados. O segundo vértice é a origem da forma (marcada *na tabela acima), exceto no caso do triângulo grande, onde (antes da rotação) ele é. -1,-1.Os outros 2 vértices podem ter coordenadas x e y -1,0 or 1extraídas da base 3 números codificados e, em seguida, redimensionados por 99 e rotacionados conforme necessário pela transformação com ce s.

Código ungolfed

  *DISPLAY L
  t=PI/8                                          :REM Constant 22.5 degrees.
  q=FNa(1)                                        :REM Call function, return dummy value to q
  END                                             :REM End the program gracefully if no solution. Absent in golfed version.

  DEFFNa(n)                                       :REM Recursive function to place shapes.
  IFn=7END                                        :REM If n=7 solution found, end program.
  LOCALk,z,j,p,i,c,s,x,y,m,u,v                    :REM declare local variables for function.
  k=ASCMID$("??O|(C",n)-64                        :REM Bitmasks for big tri, big tri, med tri, sq, normal paralellogram, small tri.
  FORz=0TO99                                      :REM For each point on the grid
    u=z MOD10*100:v=z DIV10*100                   :REM calculate its x and y coordinates relative to bottom left of screen
    ORIGINu,v                                     :REM and set the origin to this point.
    FORj=0TO12STEP4                               :REM For each rotation 0,90,180,270deg
      p=0                                         :REM assume no non-black pixels found
      FORi=j+3TOj+9STEP2                          :REM test angles of 3,5,7,9 times 22.5 deg anticlockwise from right x axis.
        c=9*COS(i*t)                             :REM Coords of test points at radius ll
        s=9*SIN(i*t)
        p*=4                                      :REM Leftshift any existing data in p
        p-=(POINT(c,s)<>0)*2+(POINT(9*c,9*s)<>0)  :REM and check pixels at radius 11 and 99.
      NEXT
      m=n                                         :REM The index of the shape to plot normally corresponds with recursion depth n.
      IF n=5 AND (43ANDp)=0 p=0:m=7               :REM If n=5 check if a reverse parallelogram is possible (mask 43). If so, clear p and change m to 7.
      REM                                         :REM Check p against mask k, if the shape fits then...
      IF (k ANDp)=0 THEN
        FOR i=-1 TO 0                               :REM draw the shape in colour, and if deeper recursions prove unsuccesful, redraw it in black.
          GCOL0,-i*n                                :REM Colour is equal to n.
          c=99*COS(j*t)                             :REM Set parameters c and s for scaling by 99
          s=99*SIN(j*t)                             :REM and rotation by 0,90,180 or 270 as appropriate.
          x=-1                                      :REM For vertex 1, x=-1 always.
          y=402/3^m MOD3-1                          :REM Lookup y value for vertex 1.
          MOVEc*x-s*y,s*x+c*y                       :REM Use c and s to transform the vertex and move to it.
          x=n<3                                     :REM For vertex 2, coords are 0,0 except for large triangle where they are -1,-1
          y=x                                       :REM in BBC BASIC, TRUE=-1
          MOVEc*x-s*y,s*x+c*y                       :REM Use c and s to transform the vertex and move to it.
          x=2778/3^m MOD3-1                         :REM Lookup x and y value for vertex 3.
          y=5775/3^m MOD3-1                         :REM PLOT85 uses last 2 points + specified point to make triangle, PLOT85+32 makes paralelogram (or square.)
          PLOT85-32*(n MOD6>3),c*x-s*y,s*x+c*y      :REM Use c and s to transform the vertex and draw shape.
          IFi q=FNa(n+1):ORIGINu,v                  :REM If i=-1 recurse to next level. If it fails, reset the origin before replotting this level's shape in black.
        NEXT
      ENDIF
    NEXT
  NEXT
  =0                                                :REM Dummy value to return from function

Saída

Esta é uma montagem das soluções encontradas pelo programa para os casos de teste. O uso de 99 em vez de 100 por razões de golfe deixa algumas pequenas lacunas negras. Como as formas são redesenhadas durante as pesquisas, pode demorar alguns segundos para executar em alguns casos, e é fascinante assistir.

insira a descrição da imagem aqui

Level River St
fonte
4
Uau, estou impressionado. Agora eu adoraria ver um vídeo dele em ação! =)
flawr 25/09/16