Este é um problema auto-referencial

49

Fórmula autorreferencial de Tupper (copiada da Wikipedia)

A fórmula auto-referencial de Tupper é uma fórmula definida por Jeff Tupper que, quando representada graficamente em duas dimensões em um local muito específico no plano, pode ser "programada" para reproduzir visualmente a própria fórmula. É usado em vários cursos de matemática e ciências da computação como um exercício de fórmulas gráficas.

Fórmula auto-referencial de Tupper

Onde chão está a função do piso.

Seja ko número de 543 dígitos a seguir: 960939379918958884971672962127852754715004339660129306651505519271702802395266424689642842174350718121267153782770623355993237280874144307891325963941337723487857735749823926629715517173716995165232890538221612403238855866184013235585136048828693337902491454229288667081096184496091705183454067827731551705405381627380967602565625016981482083418783163849115590225610003652351370343874461848378737238198224849863465033159410054974700593138339226497249461751545728366702369745461014655997933798537483143786841806593422227898388722980000748404719

Se um gráficos o conjunto de pontos (x, y)em 0 <= x < 106e k <= y < k + 17satisfazendo a desigualdade dado acima, as resultantes aparência do gráfico como este (nota que os eixos deste plano foram revertidas, caso contrário, a imagem sai de cabeça para baixo):

Resultado da fórmula autorreferencial de Tupper

E daí?

O interessante dessa fórmula é que ela pode ser usada para representar graficamente qualquer possível imagem em preto e branco de 106x17. Agora, pesquisar na pesquisa seria extremamente tedioso, então há uma maneira de descobrir o valor-k em que sua imagem aparece. O processo é bastante simples:

  1. Comece pelo pixel inferior da primeira coluna da sua imagem.
  2. Se o pixel for branco, um 0 será acrescentado ao valor k. Se estiver preto, anexe 1.
  3. Mova a coluna para cima, repetindo a etapa 2.
  4. Uma vez no final da coluna, vá para a próxima coluna e comece da parte inferior, seguindo o mesmo processo.
  5. Após a análise de cada pixel, converta essa sequência binária em decimal e multiplique por 17 para obter o valor-k.

Qual é o meu trabalho?

Seu trabalho é criar um programa que possa capturar qualquer imagem de 106x17 e gerar o valor k correspondente. Você pode fazer as seguintes suposições:

  1. Todas as imagens terão exatamente 106x17
  2. Todas as imagens conterão apenas pixels preto (# 000000) ou branco (#FFFFFF), nada no meio.

Existem algumas regras também:

  1. A saída é simplesmente o valor k. Ele deve estar na base adequada, mas pode estar em qualquer formato.
  2. As imagens devem ser lidas em PNG ou PPM.
  3. Sem brechas padrão.

Imagens de teste

[ Nintendo] deve produzir ~ 1,4946x10 542

[ Um grande número] deve produzir ~ 7.2355x10 159

[ 2 ^ 1801 * 17] deve produzir 2 1801 * 17

[ 2 ^ 1802 - 1 * 17] deve produzir (2 1802 -1) * 17

Confira este Gist para as soluções exatas.

Isso é , portanto, o menor número de bytes vence.


Links úteis

Wikipedia

Wolfram Mathworld

Kade
fonte
Posso fazer um PPM?
Maltysen
EDIT: Sim, o formato PPM é permitido. Quando criei o programa, pretendia que os PNGs fossem usados, mas permitir que o PPM permitisse a participação de mais idiomas de golfe.
Kade
3
Enquanto lia essa pergunta, antes de começar a parte "Qual é o meu trabalho", tive certeza de que vou ver a palavra em quinealgum lugar.
Jacob
Não vou fingir ser um programador que pode fazer esse tipo de coisa; em vez disso, simplesmente apresentarei uma pergunta inocente e sincera: Sim, mas isso pode ser feito ao contrário? Ou seja, alimentando a solução e vendo o * .png gerado como resultado?
@NotAsSharpAsYouGuys: se você tem uma aritmética de precisão arbitrária, é trivial, basta verificar o resultado dessa fórmula para cada pixel e exibir a imagem resultante.
Matteo Italia

Respostas:

12

CJam, 16

l,l~q:~f*/W%ze_b

Com muito obrigado a Dennis. Experimente online

Caso você esteja tendo problemas com o URL, esta é a entrada que eu testei:

P1
106 17
0000000000000000000000000000000000000000000000000000000000000000000000
0000000000000000000000000000000000000000011111100000000000000000000000
0000000000000000000000000000000000000000000000000000000000000111111000
0000011111100110000000000000000000000000000000000000000000000000000000
0000000000000000000000000110011111100000100111100001000000000000001100
0110000000000000000000000000000000000000000000000000000000001000011110
0100010011111100001000000000000100101001110000000000000000000000000000
0011000000000000000000000100001111110010010110000110001000000000000100
0110010010000000011000000000000000000100100000000000000000000100011000
0110101111000000111111000000000001000110010011111100100100111001111100
0111001011110000000000000011111100000011111111000000110111000000000001
0000100111100000110000110001100000101000001100001000000000000011101100
0000111110110000001000010000000000010010000100100110011001100100100110
0100110010011001000000000000100001000000110110011000011000010000000000
0100110001001001100110011000001001100100110010011001000000000000100001
1000011001100111111111001100000000000100110001001001100110011001111001
1001001100100110010000000000001100111111111001101111111111111100000000
0001001010010010011001100101000110011001100000110000100000000000001111
1111111111010111001001001110000000000000110001101101100110011000111001
1001100111110011110000000000000001110010010011100010001001000100000000
0000000000000000000000000000000000000000000000000000000000000000000000
1000100100010000100000000001000000000000000000000000000000000000000000
0000000000000000000000000000000000001000000000010000010000000010000000
0000000000000000000000000000000000000000000000000000000000000000000000
0001000000001000000011111111000000000000000000000000000000000000000000
0000000000000000000000000000000000000000111111110000

Usei o formato que o GIMP gerou ao exportar como ASCII pbm, com o comentário removido.

Explicação:

l,    read the first line ("P1" magic number) and get its length (2)
l~    read and evaluate the second line (106 17)
q     read the rest of the input (actual pixels)
:~    evaluate each character ('0' -> 0, '1' -> 1, newline -> nothing)
f*    multiply each number by 17
/     split into rows of length 106
W%    reverse the order of the rows
z     transpose
e_    flatten (effectively, concatenate the lines)
      now we have all the pixels in the desired order, as 0 and 17
b     convert from base 2 "digits" to a number
aditsu
fonte
Consegui no URL para você.
mbomb007
@ mbomb007 obrigado, não sei o que deu errado.
Aditsu
Se você não precisar lidar com comentários, l;l~\qN-/W%zs:~2b*deve funcionar da mesma forma.
Dennis
@ Dennis OMG, existem vários níveis de brilhantismo lá :) quer postar sozinho?
Aditsu
Não acho que uma resposta separada seja suficientemente diferente da sua.
Dennis
17

Pitão - 21 bytes

Simples de fazer com a iconversão básica de pyth . Recebe a entrada como PBMnome do arquivo e lê usando o 'comando Eu tive que usar !Mpara negar negros e brancos. Tudo o resto é auto-explicativo.

*J17i!MsC_cJrstt.z7 2

Experimente aqui online . (O intérprete da Web não pode ler os arquivos, portanto é modificado e recebe o arquivo como entrada).

Maltysen
fonte
60
Não acho que nada em Pyth seja auto-explicativo. : /
Alex A.
3
Nenhuma língua que conheço pode superar essa. Mas, novamente, nenhum dos idiomas que eu conheço é "feito para o golfe".
Mahesh
Não é possível abrir link, caminho é muito longo, Dang (Safari 8.1)
Kametrixom
Sua imagem de exemplo parece errada. Você queria usar P2 em vez de P3?
Aditsu
Oh, espere, não é mesmo P2, parece que P1 mas invertido
aditsu
9

Python 2: 133 110 bytes

Uma primeira tentativa em python usando PIL:

from PIL.Image import*
j=open(input()).load()
a=k=0
while a<1802:k=(j[a/17,16-a%17][0]<1)+k*2;a+=1
print k*17

Obrigado aos comentadores úteis abaixo

joc
fonte
2
como você usa apenas uma vez Image.open (input ()). load e não parece que você está modificando, não seria melhor usá-lo como está, em vez de usar um var j? seria algo parecido com istofrom PIL import Image k=0 for a in range(1802):y=a%17;x=a/17;k=(0 if Image.open(input()).load()[x,16-y][0]else 1)+k*2 print k*17
Katenkyo
3
Continuando no argumento de @ Katenkyo, você também pode simplesmente conectar-se a/17e a%17nos locais apropriados, e pode abusar do fato de 1 ser verdadeiro e 0 ser falso. Aqui está o resultado dessas mudanças, você vai ser até 111 bytes :)
Kade
@Kateyenko, infelizmente input()é chamado em todas as iterações do loop com essa modificação. Editando com outras dicas, obrigado.
joc
11
(...<1) --> 0**...talvez?
Sp3000 17/06/2015
7

C #, 199

Isso foi divertido! Não há nada errado em recarregar um bitmap 106 * 17 vezes, certo? Eu fiz isso como uma função para salvar alguns bytes, não tenho certeza se isso é legal.

BigInteger s(string i){return (Enumerable.Range(0,106).SelectMany(x=>Enumerable.Range(0,17).Select(y=>new BigInteger(new Bitmap(i).GetPixel(x,y).B==0?1:0)).Reverse()).Aggregate((x,y)=>(x<<1)+y)*17);}

i é o nome do arquivo de entrada.

Além disso, como uma expressão única, apenas porque é uma expressão, com ifornecida ou subbedada (167 bytes)

(Enumerable.Range(0,106).SelectMany(x=>Enumerable.Range(0,17).Select(y=>new BigInteger(new Bitmap(i).GetPixel(x,y).B==0?1:0)).Reverse()).Aggregate((x,y)=>(x<<1)+y)*17)
DLeh
fonte
11
A questão diz "seu trabalho é criar um programa ..."
Sean Latham
1

Mathematica 69 Bytes

17*FromDigits[1-Flatten[Reverse/@Transpose[ImageData@Binarize@#]],2]&

O Binarize @ pode ficar de fora se a imagem estiver no formato monocromático.

Esta função irá reproduzir a imagem:

   ArrayPlot[Table[Boole[1/2<Floor[Mod[Floor[y/17]2^(-17Floor[x]-Mod[Abs[y],17]),2]]],{y,1+#,17+#},{x,106,1,-1}]]&
Kelly Lowder
fonte