Rebmu : 79 karakter OR (37 + uzunluk (p1) + 2 * maks (uzunluk (p2), uzunluk (p3)))
İlk önce, hangi dilleri öğrenmelisin diye soran 79 karakterli bir çözüm vereceğim. (entropi 4.0, 30 harf dahil değil ?
) ve Rebol ve [Red] ' in önerilerini sunar :
DD 11 DD :do dd {dd {p{Which languages must you learn?}qt}} pp{{[RReebdo]l}}
Burada başka dillerde bulunmayan eşsiz bir taktik, kaşlı ayraçların yasal olarak yuvalanabilen asimetrik bir tel sınırlayıcı olması gerçeğinden yararlanmaktan geliyor:
my-string: {"It's cool," said {Dr. Rebmu}, "for MANY reasons--like less escaping."}
Bu, kaçış dizileri kullanmayan herhangi bir program üzerinde zahmetsizce çalışabilen genel bir çözüm üretmeme izin verdi. 79 karakter sürümü kısayol için yeterince basitti, ancak p2 ve p3 programları için rasgele bir program kaynağı içermek için tam şablona ihtiyacınız olacaktı. Bunu kullanmış olsaydık, 87 karakter olurdu:
DD 11 DD :do dd {dd {p{Which languages must you learn?}qt}} ddoo{{pp{{[RReebdo]l}}}}
Bu genel formu kullanarak için desen değişken uzunluktaki ardışık karakterlerin üç kaynak metinleri varsa (en gibi bir örnek kullanmasına izin olmasıdır AAA
, BBBBB
, CCCCCCC
sen çizgisinde bir şey olarak onları kodlamak):
DD 11 DD :do dd {dd {AAAqt}} ddoo{{BCBCBCBCBC C C}}
(Not:. Bu model kullanımı kaçış karakterleri, bu ölümcül kusur programlarına ince ayarlar olmadan değil işin değil ki olsa parantez ile sınırlanmış bir dizede eşsiz sol ayracı alma gibi bir şey gerektirir {Foo ^{ Bar}
... ancak kolayca kullanarak bu yazabilirsiniz alternatif dize notasyonu "Foo { Bar"
ve birleşik durumlar, birlikte çıkmamış dizelerin bir karışımının yapıştırılmasıyla birlikte yönetilebilir.)
Peki ... peki ya bir örnek? Genel form kullanıma sunulduktan sonra, bu 573 karakter programı, önceki 3 kod golf çözümünden sadece birkaç dakika içinde toplandı:
DD 11 DD: dd {dd {rJN% 0 rN Wa1m2jS {{x /} D00 Hc & [u [Ze? Wa Qs ~ rpKw [isEL00c [skQd2k] [eEV? KQ [tlQ]] pcSeg - b00 [ eZ 1 5] 3] prRJ [siSdscSqFHs] eZ 1 [s + dCa + wM2cNO]]] Va | [mpAp2j] prSI ~ w { } Ls2w Wl h01tiVsb01n-1 chRVs { } hLceVn01qtdb {dd . {K, j} b P {. } lf EZ - - n [N m {G otothestoreandbuysome daha fazla}] {T akeonedownandpassitar ound} c B w P lf]]}}
Herhangi biri bu programı tercih ettiği dilde yazmayı denemek istiyorsa ve 573'ü geçebileceğini düşünüyorsa, bana bildirin. Seçim dilinizin Rebmu olmadığını varsayarsanız, bu programların asgari düzeyde olmadığını biliyorum çünkü, size ağır bir üne sahip olacağım. :-)
Sonunda elde ettiğiniz "boşa harcanan" boşluk, p2 ve p3 dengesiz uzunluklarda olduğunda gerçekleşen şeydir. Ancak bu 3 program da farklı boyutlardadır, bu nedenle p2 / p3 için seçilecek belirli bir eşleşme yoktur. (Bunları seçtim çünkü labirent veya başka herhangi bir girdi gibi harici veri yoktu, benzer uzunluklarda olmadılar. Daha uygun yeni programlar yazabildiğim halde, yeterince zaman harcadım ve asıl konu şuydu: Eğer yok yeni programlar yazmak zorunda ...)
Nasıl çalışır
(Not: Daha akıcı olmayan ama daha ilginç görünen, daha "yaratıcı" bir yaklaşımla başladım. Bu yaklaşımı açıklayan uzun sürdüğü için blogumdaki bir girişe taşıdım .)
Buradaki anahtar diğer bazı girişler gibi "hileli değerlendirme kodu" gibi bir hiledir, sadece asimetrik string sınırlayıcının koz kartına sahiptir. 80 karakterlik vakanın çalışmalarını açıklayarak başlayacağım.
İşte bu "bütün" program, bu davanın okunabilirliği için boşlukları ayarlıyor:
DD 11 ; assign 11 to dd (about to overwrite again)
DD :do ; make dd a synonym for DO (a.k.a. "eval")
; eval a string as source code that ends with QUIT (QT)
dd {dd {p{Which languages must you learn?}qt}}
; we'll never get here, but whatever's here must be legally parseable
pp{{[RReebdo]l}}
Burada DD'yi DO (aka "eval") ile eşanlamlı olarak ayarlıyoruz. Ancak işin püf noktası, yarı yarıya programlar çalıştığında, tek etkisi D'yi zararsız değişmez 1 olarak tanımlamak için çalışan kodları kurmalarıdır.
İşte garip karakter kodunun yaptığı şey: boşluklar yeniden ayarlandı:
D 1 ; assign 1 to d
D d ; assign d to itself, so it's still 1
d ; evaluates to integer, no side effect
{d pWihlnugsms o er?q} ; string literal, no side effect
p {Rebol} ; print "Rebol"
Ve işte eşit karakter kodu:
D 1 ; assign 1 to d
D:od ; URL-literal (foo:...), no side effect
d ; evaluates to integer, no side effect
{{hc agae utyulan}t} ; string literal (well-formed!), no side effect
p {[Red]} ; print "[Red]"
Aslına bakarsanız yarı yarıya olmayan program için, dd {dd {(arbitrary code)qt}}
istediğiniz kodu çalıştıracaktır. Ancak, sadece bir tane yerine değerlendirilecek iki çağrı var. Bunun nedeni, iç içe geçmiş parantezlerin eklenmiş kodda çok iyi çalışmasına rağmen, DO'nun değerlendirme davranışını karıştırdıklarıdır. Çünkü:
do {{print "Hello"}}
Dizeyi bir program olarak yükleyecektir, ancak bu program yalnızca dize sabiti olarak görünmektedir {print "Hello"}
. Bu yüzden burada kullandığım numara DD'imi almak (DO ile aynı fonksiyon değerini tutmak) ve iki kere çalıştırmak. Körükler ipin farklı kısımlarında çiğniyorlar ancak içerik için çift / tuhaflık doğru ise her ikisini de çiğniyorlar ve yarıya çıktıktan sonra ipin dışında kalanlar sadece integral sabiti d
olduğu için zararsızlar.
Bu kalıpla, ikiye bölünmediğinde program davranışını yazma konusunda zorluk yoktur - kodun karakter uzunluğu eşit olduğu sürece herhangi bir şeyi koyabilirsiniz (QTIT olan QT'yi sayarsanız garip). Tek bir sayıdan çift sayı almanız gerekiyorsa, bir boşluk koyun (p1'deki tuhaf program uzunlukları için yukarıdaki formülümde aslında bir +1 var) . İşin hilesi eğer ayrıştırıcı geçmek zorunda olduğu, daha sonra o serpiştirilmiş kod yazmak gibi görünüyor değildir yarıya. (QT nedeniyle çalıştırılmayacak, ancak çalıştırılmadan önce YÜKLE olması gerekiyor.)
Bu dava önemsizdir; pp
tanımlanmamış olmasına rağmen bir simge olarak iyi yükler ve p
her yarım programda yazdırmak için ayrılmıştır . Fakat yine de sadece bir string string kullanarak başka bir numara yapabiliriz. Yarıda bırakılmış programlar hala normal olarak DO tanımladı, bu yüzden de şunu söyleyebiliriz:
ddoo{{pp{{[RReebdo]l}}}}
Çözümleyici tarafından ele alınan tek kısmı tümüyle sembolik bir sözcük ddoo
ve bir dize değişmezi haline getirerek, bu dize değişmezinde istediğimiz iki programı birleştirebilir ve çözümleyiciyi öfkelendirmeyebiliriz. Yarıya indirilmiş versiyonlar şöyle der:
do{p{Rebol}}
..ve...
do{p{[Red]}}
Dediğim gibi, bu bölüm programları dizeler olarak değerlendiren ve değerlendiren diğer çözümlere aşina görünüyor. Ancak, rekabet durumunda, paketlemekte olduğunuz programlar iç içe diziler içerdiğinde, bunlar için anahtarlar atarlar. Burada başınızı belaya sokacak olan tek şey, ^
etrafta kolayca çalışılabilecek olan ( ) ( ).
(Küçük 'hile' notu: Bu soruna cevaben "ÇIKIŞ" için QT ekledim. Aslında, daha önce bırakma kısaltmasını bilerek kaldırmıştım ... çünkü bir şekilde bunun sadece konsol kullanımı için iyi olduğunu düşündüm. Eğer bir REPL'de olmasaydı iki harflik boşluk ekledim, ekliyorum çünkü yanıldım, özellikle bu dava için ekleyemedim, yine de, bu değişiklikten önce 2 karakter daha uzun olurdu. Çözümü ilk gönderdiğimde Rebmu'da olması gerekmesine rağmen çalışmasını engelleyen bir hata vardı ... şimdi çalışıyor.)
x0=00;;
. Büyük zorluk!