Domanda

Ho visto molte soluzioni basate su C / C ++ a questo problema in cui dobbiamo scrivere un programma che al momento dell'esecuzione stampa la propria fonte.

alcune soluzioni -

http://www.cprogramming.com/challenges/solutions/self_print.html

Soluzione Quine Page in molte lingue

Esistono molte più soluzioni in rete, ognuna diversa dall'altra. Mi chiedo come affrontiamo un problema del genere, ciò che passa nella mente di chi lo risolve. Mi dia alcune informazioni su questo problema ... Mentre le soluzioni in linguaggi interpretati come perl, php, ruby, ecc. Potrebbero essere facili ... vorrei sapere come si fa a progettarlo in linguaggi compilati ...

È stato utile?

Soluzione

Oltre a barare & # 185; non c'è differenza tra le lingue compilate e interpretate.

L'approccio generico ai quines è abbastanza semplice. Innanzitutto, qualunque sia il programma, a un certo punto deve stampare qualcosa:

print ...

Tuttavia, cosa dovrebbe stampare? Si. Quindi deve stampare la "stampa" comando:

print "print ..."

Cosa dovrebbe stampare dopo? Bene, nel frattempo il programma è cresciuto, quindi deve stampare la stringa iniziando anche con " print " ;,

print "print \"print ...\""

Ora il programma è cresciuto di nuovo, quindi c'è ancora molto da stampare:

print "print \"print \\\"...\\\"\""

E così via. Con ogni codice aggiunto c'è più codice da stampare. Questo approccio non sta andando da nessuna parte, ma rivela uno schema interessante: La stringa " print \ " " viene ripetuto più volte. Sarebbe bello mettere la parte ripetuta in una variabile:

a = "print \""
print a

Tuttavia, il programma è appena cambiato, quindi dobbiamo regolare a:

a = "a = ...\nprint a"
print a

Quando proviamo ora a compilare " ... " ;, ci imbattiamo negli stessi problemi di prima. Alla fine, vogliamo scrivere qualcosa del genere:

a = "a = " + (quoted contents of a) + "\nprint a"
print a

Ma ciò non è possibile, perché anche se avessimo una tale funzione quoted () per la quotazione, c'è ancora il problema che definiamo a in termini di se stesso:

a = "a = " + quoted(a) + "\nprint a"
print a

Quindi l'unica cosa che possiamo fare è mettere un segnaposto in a :

a = "a = @\nprint a"
print a

E questo è tutto il trucco! Ora è chiaro tutto il resto. Sostituisci semplicemente il segnaposto con i contenuti citati di a :

a = "a = @\nprint a"
print a.replace("@", quoted(a))

Poiché abbiamo modificato il codice, dobbiamo regolare la stringa:

a = "a = @\nprint a.replace(\"@\", quoted(a))"
print a.replace("@", quoted(a))

E questo è tutto! Tutti i quines in tutte le lingue funzionano in questo modo (tranne quelli che tradiscono).

Bene, dovresti assicurarti di sostituire solo la prima occorrenza del segnaposto. E se usi un secondo segnaposto, puoi evitare di dover citare la stringa.

Ma quelli sono problemi minori e facile da risolvere. In realtà, la realizzazione di quoted () e replace () sono gli unici dettagli in cui le varie quine differiscono davvero.


& # 185; facendo leggere il file sorgente al programma

Altri suggerimenti

Ci sono un paio di strategie diverse per scrivere quines. L'ovvio è semplicemente scrivere il codice che apre il codice e lo stampa. Ma quelli più interessanti riguardano funzionalità linguistiche che consentono l'autoincorporamento, come la funzione printf in stile% s in molte lingue. Devi capire come incorporare qualcosa in modo che si risolva con la richiesta di essere incorporato. Sospetto che, come i palindromi, siano coinvolti molti tentativi ed errori.

Inoltre puoi studiare come funziona il gioco Core Wars. Sarebbe un buon esempio, credo.

L'approccio abituale (quando non puoi imbrogliare *) è scrivere qualcosa che codifica la sua fonte in una costante di stringa, quindi stampa quella costante due volte: una volta come stringa letterale e una volta come codice. Ciò aggira il " ogni volta che scrivo una riga di codice, devo scriverne un altro per stamparlo! & Quot; problema.

'Cheating' include: - Utilizzando una lingua interpretata e semplicemente caricando la fonte e stampandola - File lunghi 0 byte, che sono validi in alcune lingue, come C.

Per divertimento, ne ho trovato uno in Scheme, di cui sono stato abbastanza orgoglioso per circa 5 minuti fino a quando ho scoperto che è stato scoperto prima. Ad ogni modo, c'è una leggera modifica alle regole di "quotazione" del gioco per contare meglio la dualità di dati e codice in Lisp: invece di stampare l'origine del programma, è un'espressione S che restituisce se stessa:

((lambda (x) (list x `',x)) '(lambda (x) (list x `',x)))

Il uno su Wikipedia ha lo stesso concetto, ma con un meccanismo leggermente diverso (più dettagliato) per la quotazione. Mi piace di più il mio.

Un'idea per pensare alla codifica e come dare a qualcosa un doppio significato in modo che possa essere usata per produrre qualcosa in un paio di forme. C'è anche il cavaet che questo tipo di problema comporta delle restrizioni per renderlo più difficile poiché, senza regole diverse dall'output del programma stesso, il programma vuoto è una soluzione.

Puoi trovare parecchie soluzioni a questo qui: http: // forums.thedailywtf.com/forums/p/5232/147528.aspx

Che ne dici di leggere e stampare il tuo codice sorgente? Non è affatto difficile !! Eccone uno in php:

<?php
{
header("Content-Type: text/plain");
    $f=fopen("5.php","r");
    while(!feof($f))
    {
        echo fgetc($f);
    } 
    fclose($f);
}
?>

In Python puoi scrivere:

s='c=chr(39);print"s="+c+s+c+";"+s';c=chr(39);print"s="+c+s+c+";"+s

ispirato da questo pseudo-codice auto-stampa:

Print the following line twice, the second time with quotes.
"Print the following line twice, the second time with quotes."

Ho fatto un esempio AS3 per coloro che sono interessati a questo

var program = "var program = @; function main(){trace(program.replace('@', 

String.fromCharCode(34) + program + String.fromCharCode(34)))} main()"; 
function main(){
   trace(program.replace('@', String.fromCharCode(34) + program + String.fromCharCode(34)))
}
main()

In rubino:

inserisce File.read (_ _ FILE _ _)

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top