Bu Kendinden Referanslı Bir Sorun


49

Tupper'ın Kendine Referans Formülü (Wikipedia'dan kopyalandı)

Tupper'ın kendine referans formülü, Jeff Tupper tarafından tanımlanan, düzlemde çok spesifik bir konumda iki boyutta çizildiğinde, formülün kendisini görsel olarak çoğaltmak için "programlanabilen" bir formüldür. Çeşitli matematik ve bilgisayar bilimleri derslerinde grafik formüllerinde alıştırma olarak kullanılır.

Tupper'ın Kendine Referans Formülü

zemin Zemin işlevi nerede .

Let kşu 543 haneli sayı: 960939379918958884971672962127852754715004339660129306651505519271702802395266424689642842174350718121267153782770623355993237280874144307891325963941337723487857735749823926629715517173716995165232890538221612403238855866184013235585136048828693337902491454229288667081096184496091705183454067827731551705405381627380967602565625016981482083418783163849115590225610003652351370343874461848378737238198224849863465033159410054974700593138339226497249461751545728366702369745461014655997933798537483143786841806593422227898388722980000748404719

Biri , yukarıda verilen eşitsizliği (x, y)gösteren 0 <= x < 106ve k <= y < k + 17tatmin eden nokta kümesini çiziyorsa, sonuçtaki grafik şöyle görünür (bu çizimdeki eksenlerin tersine çevrildiğine dikkat edin, aksi halde resim ters çıkar):

Tupper'ın Kendine Referans Formülü Sonucu

Ne olmuş yani?

Bu formülle ilgili ilginç olan şey, olası herhangi bir siyah beyaz 106x17 görüntüsünü grafik haline getirmesidir. Şimdi, aslında arama yapmak için arama yapmak çok sıkıcı olacak, görüntünüzün göründüğü yerde k değerini anlamanın bir yolu var. İşlem oldukça basittir:

  1. Resminizin ilk sütununun alt pikselinden başlayın.
  2. Eğer piksel beyaz ise, k değerine 0 eklenir. Siyahsa, 1 ekleyin.
  3. 2 numaralı adımı yineleyerek sütunu yukarı kaldırın.
  4. Sütunun sonunda bir sonraki sütuna geçin ve aynı işlemi takip ederek alttan başlayın.
  5. Her piksel analiz edildikten sonra, bu ikili dizgeyi ondalık değere dönüştürün ve k değerini elde etmek için 17 ile çarpın.

Mesleğim ne

İşiniz, herhangi bir 106x17 görüntü alabilen bir program oluşturmak ve karşılık gelen k değerini vermektir. Aşağıdaki varsayımları yapabilirsiniz:

  1. Tüm resimler tam 106x17 olacak
  2. Tüm resimler yalnızca siyah (# 000000) veya beyaz (#FFFFFF) piksel içerecek, aralarında hiçbir şey olmayacaktır.

Birkaç kural da var:

  1. Çıktı basitçe k-değeridir. Uygun bir temelde olmalıdır, ancak herhangi bir formatta olabilir.
  2. Görüntüler bir PNG veya PPM'den okunmalıdır.
  3. Standart boşluklar yok.

Test görüntüleri

[ Nintendo] ~ 1.4946x10 542 üretmeli

[ Büyük bir sayı] ~ 7.2355x10 159 üretmeli

[ 2 ^ 1801 * 17] 2 1801 * 17 üretmeli

[ 2 ^ 1802 - 1 * 17] üretmeli (2 1802 -1) * 17

Kesin çözümler için bu Gist'i inceleyin.

Bu , yani en az bayt sayısı kazanır.


Faydalı Bağlantılar

Vikipedi

Wolfram Mathworld


PPM alabilir miyim?
Maltysen

EDIT: Evet, PPM formatına izin verilir. Programla karşılaştığımda, PNG'lerin kullanılmasını istedim, ancak PPM'ye izin vermek, daha fazla golf dilinin katılımına izin vermelidir.
Kade

3
Bu soruyu okuduğumda, "Mesleğim ne" bölümüne gelmeden önce, bir quineyerde kelimeyi göreceğime eminim .
Jacob

Bu tür şeyleri yapabilen bir programcı gibi davranmayacağım, bunun yerine sadece masum ve ciddi bir soru sunacağım: Evet, ama tersten yapılabilir mi? Yani çözelti içinde besleniyor ve sonuç olarak ortaya çıkan * .png'yi görüyorsunuz?

@NotAsSharpAsYouGuys: Keyfi hassas aritmetik varsa önemsiz, sadece her piksel için bu formülün sonucunu kontrol etmeniz ve elde edilen görüntüyü vermeniz yeterlidir.
Matteo Italia

Yanıtlar:


12

CJam, 16

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

Dennis'e büyük teşekkürler. Çevrimiçi deneyin

URL ile ilgili sorun yaşıyorsanız, test ettiğim giriş:

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

Yorumun kaldırılmasıyla GIMP'nin ASCII pbm olarak dışa aktarırken oluşturduğu formatı kullandım.

Açıklama:

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

URL’yi sizin için aldım.
mbomb007

@ mbomb007 teşekkürler, neyin yanlış gittiğinden emin değilim.
aditsu

Yorumlarla uğraşmak zorunda değilseniz, l;l~\qN-/W%zs:~2b*aynı şekilde çalışmalısınız.
Dennis

@Dennis OMG, orada birkaç parlaklık seviyesi var :) kendiniz göndermek ister misiniz?
aditsu

Ayrı bir cevabın seninkinden yeterince farklı olacağını sanmıyorum.
Dennis

17

Pyth - 21 bayt

Pyth'un itemel dönüşümü ile yapmak kolaydır . Girdiyi PBMdosya adı olarak alır ve 'komutu kullanarak okur . !MSiyahları ve beyazları olumsuzlamak için kullanmak zorunda kaldım . Geriye kalan her şey açıklayıcıdır.

*J17i!MsC_cJrstt.z7 2

Burada çevrimiçi deneyin . (Web tercümanı dosyaları okuyamaz, bu yüzden değiştirilir ve dosyayı girdi olarak alır).


60
Pyth'taki hiçbir şeyin açıklayıcı olduğunu düşünmüyorum . : /
Alex A.

3
Bildiğim hiçbir dil bunu yenemez. Ama sonra yine bildiğim hiçbir dilde "golf için yapılmış" değil.
Mahesh

Bağlantı açılamıyor, yol çok uzun,
sarkma

Örnek resminiz yanlış görünüyor. P3 yerine P2 kullanmak mı istediniz?
aditsu

Bekle, P2 bile değil, P1'e benziyor ama ters çevrilmiş
aditsu

9

Python 2: 133 110 bayt

PIL kullanarak python ilk girişimi:

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

Aşağıdaki yararlı yorumculara teşekkürler


2
Sadece bir kez kullandığınız Image.open (input ()) .load ve değiştirdiğiniz gibi görünmüyor, var j kullanmak yerine, olduğu gibi kullanmak daha iyi olmaz mıydı? böyle bir şey olurdufrom 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
Katenkyo gözüyle @ Devam edersek, ayrıca sadece takabilirsiniz a/17ve a%17uygun yerlerde ve 1 truthy ve 0 falsy olduğu gerçeğini kötüye kullanabilir. İşte bu değişikliklerin sonucu, 111
Kade

@Kateyenko, ne yazık ki input()bu değişiklik ile döngünün her yinelemede çağrılır. Diğer ipuçları ile düzenleme olsa da, teşekkür ederim.
haziran

1
(...<1) --> 0**...olabilir?
Sp3000,

7

C #, 199

Bu komikti! Bitmap'i 106 * 17 kez yeniden yüklemede yanlış bir şey yok, değil mi? Bazı baytları kurtarmak için bir işlev olarak yaptım, yasal olup olmadığından emin değilim.

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 giriş dosyası adıdır.

Ayrıca, tek bir ifade olarak, sadece tek bir ifade olduğundan, isağlanan veya alt yatağıyla (167 bayt)

(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)

1
Soru, "işiniz bir program oluşturmaktır ..." diyor
Sean Latham

1

Mathematica 69 Bayt

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

Görüntü siyah beyaz formattaysa, Binarize @ bırakılabilir.

Bu işlev görüntüyü çoğaltacaktır:

   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}]]&
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.