Rebmu : 79 caratteri OR (37 + lunghezza (p1) + 2 * max (lunghezza (p2), lunghezza (p3)))
Per prima cosa fornirò una soluzione di 79 caratteri che chiede quali lingue devi imparare? (entropia 4.0, 30 lettere escluse ?
) e ti offre i suggerimenti di Rebol e [Rosso] :
DD 11 DD :do dd {dd {p{Which languages must you learn?}qt}} pp{{[RReebdo]l}}
Una tattica unica disponibile qui che non è in altre lingue deriva dal fatto che le parentesi graffe sono un delimitatore di stringa asimmetrico, che può nidificare legalmente:
my-string: {"It's cool," said {Dr. Rebmu}, "for MANY reasons--like less escaping."}
Ciò mi ha permesso di produrre una soluzione generalizzata, che può funzionare senza sforzo su qualsiasi programma che non utilizza sequenze di escape. La versione a 79 caratteri era abbastanza semplice da scorciatoia, ma per contenere correttamente l'origine di programma arbitraria per i programmi p2 e p3 avresti bisogno del modello completo. Se lo avessimo usato, sarebbero stati 87 caratteri:
DD 11 DD :do dd {dd {p{Which languages must you learn?}qt}} ddoo{{pp{{[RReebdo]l}}}}
Il modello per l'utilizzo di questa forma generale è che se si dispone di tre testi originali di personaggi sequenziali di lunghezza variabile (usiamo un esempio come AAA
, BBBBB
, CCCCCCC
) si possono codificare come qualcosa sulla falsariga di:
DD 11 DD :do dd {dd {AAAqt}} ddoo{{BCBCBCBCBC C C}}
(Nota: anche se questo schema non funzionerà senza modificare i programmi che usano caratteri di escape, questo non è un difetto fatale. Ottenere una parentesi graffa sinistra senza pari in una stringa delimitata da parentesi graffe richiede qualcosa di simile {Foo ^{ Bar}
... ma si potrebbe facilmente riscrivere che usando la notazione di stringa alternativa "Foo { Bar"
e i casi combinati possono essere gestiti incollando insieme una combinazione di stringhe senza caratteri di escape.)
Quindi ... che ne dici di un esempio? Una volta disponibile il modulo generale, questo programma di 573 caratteri è stato assemblato in un paio di minuti da 3 precedenti soluzioni di golf di codice:
DD 11 DD: do dd {dd {rJ N 0% rN Wa1m2j S {\ x /} D00 Hc & [u [Ze? Wa Qs ~ rpKw [isEL00c [skQd2k] [eEV? KQ [tlQ]] pcSeg - b00 [ eZ 1 5] 3] prRJ [si ~ dSPscSqFHs] eZ 1 [s + dCa + wM2cNO]]] Va | [mpAp2j] prSI ~ w { } Ls2w Wl h01tiVsb01n -1 chRVs { } hLceVn01qt}} ddoo {{BrdS [sn [{N sbeo [tIt0l1eV} 0e5gXN1 01L {5s0} C {1} 0 {0 Do5f0 0bMe1e0r0} 0]]] tMw9C9 Numz Jl [paN + [KperlCJBn [a ba sWS {B noJn Nn]]] {K, j} b P {. } lf EZ - - n [N m {G ototestoreandbuysome more}] {T akeonedownandpassitar ound} c B w P lf]]}}
Se qualcuno vuole provare a scrivere quel programma nella loro lingua preferita e pensa di poter battere 573, fammelo sapere. Se lo farai, ti darò una grande reputazione - supponendo che la tua lingua preferita non sia Rebmu, perché so che quei programmi non sono minimi. :-)
Quella spaziatura "dispendiosa" che ottieni alla fine è ciò che accade quando p2 e p3 hanno lunghezze squilibrate. Ma tutti e 3 i programmi hanno dimensioni diverse in questo caso, quindi non esiste un abbinamento particolarmente valido da scegliere per p2 / p3. (Ho scelto questi perché non c'erano dati esterni come input, come un labirinto o altro, non che fossero di lunghezza simile. Mentre avrei potuto scrivere nuovi programmi che erano più ottimali, ho trascorso abbastanza tempo e il punto era non devi scrivere nuovi programmi ...)
Come funziona
(Nota: ho iniziato con un approccio più "creativo" che non era così snello ma più interessante. L'ho spostato in una voce sul mio blog in quanto la descrizione di questo approccio è già lunga.)
Una chiave qui è l'inganno "codice eval come stringa" come alcune altre voci, ha solo la carta vincente del delimitatore di stringa asimmetrica. Inizierò spiegando il funzionamento del caso di 80 caratteri.
Ecco il programma "intero", che regola lo spazio per la leggibilità di questo caso:
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}}
Qui finiamo per impostare DD su un sinonimo di DO (aka "eval"). Ma il trucco è che quando vengono eseguiti i programmi divisi in due, finiscono per eseguire il codice il cui unico effetto è definire D al letterale innocuo 1.
Ecco cosa rende il codice dei caratteri dispari, lo spazio bianco è nuovamente regolato:
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"
Ed ecco il codice dei caratteri pari:
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]"
In realtà è il caso che per il programma non dimezzato, dd {dd {(arbitrary code)qt}}
eseguirà qualsiasi codice tu voglia. Tuttavia, ci sono due chiamate da valutare invece di una sola. Questo perché mentre le parentesi graffe nidificate funzionano benissimo nel codice interfogliato, confondono il comportamento eval di DO. Perché:
do {{print "Hello"}}
Caricherà la stringa come programma, ma quel programma finisce per essere solo la costante di stringa {print "Hello"}
. Quindi il trucco che uso qui è prendere il mio DD (mantenendo lo stesso valore di funzione di DO) ed eseguirlo due volte. I halver masticano le diverse parti della stringa ma non masticano entrambi se la dispari / dispari è corretta per il contenuto, e poiché ciò che rimane fuori dalla stringa dopo il dimezzamento è solo la costante integrale d
sono innocui.
Con questo modello non c'è alcuna sfida nello scrivere il comportamento del programma quando non è tagliato a metà: puoi inserire qualsiasi cosa fintanto che la lunghezza dei caratteri del codice è pari (strano se stai contando il QT, che è QUIT). Se hai bisogno di ottenere il numero pari da uno dispari, lancia uno spazio (quindi in realtà c'è un +1 nella mia formula sopra su p1 per lunghezze di programma dispari di p1) . Il trucco sembrerebbe scrivere quel codice interlacciato in seguito, che deve passare al parser se non viene dimezzato. (Non verrà eseguito a causa del QT, ma deve essere CARICABILE prima che venga eseguito.)
Questo caso è banale; pp
carica bene come simbolo anche se non definito, ed è suddiviso p
per la stampa in ogni mezzo programma. Ma possiamo fare un altro trucco semplicemente usando di nuovo una stringa letterale. I programmi dimezzati hanno ancora DO definito normalmente, quindi avremmo potuto anche solo dire:
ddoo{{pp{{[RReebdo]l}}}}
Avendo l'unica parte raccolta dal parser in tutto il caso essere la parola simbolica ddoo
e una stringa letterale, possiamo quindi intercalare tutti i due programmi che desideriamo all'interno di quella stringa letterale e non far arrabbiare il parser. Le versioni dimezzate diranno solo:
do{p{Rebol}}
..e...
do{p{[Red]}}
Come ho già detto, questa parte sembra familiare ad altre soluzioni che trattano i programmi come stringhe e li valutano. Ma nel caso della competizione, quando i programmi che stai confezionando contengono stringhe nidificate, ciò genera una chiave inglese per loro. Qui le uniche cose che ti metteranno nei guai sono l'uso dell'evasione tramite i punti di inserimento ( ^
) ... che possono essere facilmente risolti .
(Piccola nota 'imbroglione': ho aggiunto QT per "ESCI" in risposta a questo problema. In realtà, avevo rimosso intenzionalmente l'abbreviazione per smettere prima ... perché in qualche modo ho pensato che fosse buono solo per l'uso della console e semplicemente riprendendo il spazio di due lettere se non fosse in un REPL. Lo sto aggiungendo perché vedo che mi sbagliavo, non lo ho aggiunto per questo caso in particolare. Tuttavia, prima di tale modifica, sarebbero stati più lunghi di 2 caratteri. quando ho pubblicato per la prima volta la soluzione c'era un bug in Rebmu che gli impediva di funzionare davvero anche se avrebbe dovuto ... ora funziona.)
x0=00;;
. Grande sfida!