Quine (computing): Difference between revisions

From Wikipedia, the free encyclopedia
Content deleted Content added
No edit summary
 
(44 intermediate revisions by 34 users not shown)
Line 1: Line 1:
{{short description|Self-replicating program}}
{{Short description|Self-replicating program}}
[[File:Java implementation of a quine program.png|thumb|300px|A quine's output is exactly the same as its source code. (Note that the [[syntax highlighting]] demonstrated by the [[text editor]] in the upper half of the image does not affect the output of the quine.)]]


[[File:Java implementation of a quine program.png|thumb|300px|A quine's output is exactly the same as its source code (the [[syntax highlighting]] demonstrated by the [[text editor]] in the upper half of the image does not affect the output of the quine).]]
A '''quine''' is a [[computer program]] which takes no input and produces a copy of its own [[source code]] as its only output. The standard terms for these programs in the [[computability theory]] and [[computer science]] literature are "self-replicating programs", "self-reproducing programs", and "self-copying programs".
A '''quine''' is a [[computer program]] that takes no input and produces a copy of its own [[source code]] as its only output. The standard terms for these programs in the [[computability theory]] and [[computer science]] literature are "self-replicating programs", "self-reproducing programs", and "self-copying programs".


A quine is a [[Fixed point (mathematics)|fixed point]] of an execution environment, when the execution environment is viewed as a [[Function (mathematics)|function]] transforming programs into their outputs. Quines are possible in any [[Turing completeness|Turing-complete]] programming language, as a direct consequence of [[Kleene's recursion theorem]]. For amusement, programmers sometimes attempt to develop the shortest possible quine in any given [[programming language]].
A quine is a [[Fixed point (mathematics)|fixed point]] of an execution environment, when that environment is viewed as a [[Function (mathematics)|function]] transforming programs into their outputs. Quines are possible in any [[Turing completeness|Turing-complete]] programming language, as a direct consequence of [[Kleene's recursion theorem]]. For amusement, programmers sometimes attempt to develop the shortest possible quine in any given [[programming language]].

== Name ==


The name "quine" was coined by [[Douglas Hofstadter]], in his popular science book ''[[Gödel, Escher, Bach]]'', in honor of philosopher [[Willard Van Orman Quine]] (1908–2000), who made an extensive study of [[indirect self-reference]], and in particular for the following paradox-producing expression, known as [[Quine's paradox]]:
The name "quine" was coined by [[Douglas Hofstadter]], in his popular science book ''[[Gödel, Escher, Bach]]'', in honor of philosopher [[Willard Van Orman Quine]] (1908–2000), who made an extensive study of [[indirect self-reference]], and in particular for the following paradox-producing expression, known as [[Quine's paradox]]:
Line 13: Line 15:


==History==
==History==
The idea of [[Von Neumann universal constructor|self-reproducing automata]] came from the dawn of computing, if not before. [[John von Neumann]] theorized about them in the 1940s. Later, [[Paul Bratley]] and Jean Millo's article "Computer Recreations: Self-Reproducing Automata" discussed them in 1972.<ref name="Bratley_Millo">{{cite journal | last1 = Bratley
The idea of [[Von Neumann universal constructor|self-reproducing automata]] came from the dawn of computing, if not before. [[John von Neumann]] theorized about them in the 1940s. Later, Paul Bratley and Jean Millo's article "Computer Recreations: Self-Reproducing Automata" discussed them in 1972.<ref name="Bratley_Millo">{{cite journal | last1 = Bratley
| first1 = Paul
| first1 = Paul
| author-link1 = Paul Bratley
| author-link1 = Paul Bratley
Line 27: Line 29:
| s2cid = 222194376
| s2cid = 222194376
}}</ref>
}}</ref>
Bratley first became interested in self-reproducing programs after seeing the first known such program written in [[Atlas Autocode]] at Edinburgh in the 1960s by the [[University of Edinburgh]] lecturer and researcher [[Hamish Dewar]].
Bratley first became interested in self-reproducing programs after seeing the first known such program written in [[Atlas Autocode]] at Edinburgh in the 1960s by the [[University of Edinburgh]] lecturer and researcher Hamish Dewar.


The "download source" requirement of the [[Affero General Public License]] is based on the idea of a quine.<ref name="Stet_and_AGPLV3">{{cite web
The "download source" requirement of the [[GNU Affero General Public License]] is based on the idea of a quine.<ref name="Stet_and_AGPLV3">{{cite web
| url = http://www.softwarefreedom.org/technology/blog/2007/nov/21/stet-and-agplv3/
| url = http://www.softwarefreedom.org/technology/blog/2007/nov/21/stet-and-agplv3/
| title = stet and AGPLv3
| title = stet and AGPLv3
Line 47: Line 49:
In general, the method used to create a quine in any programming language is to have, within the program, two pieces: (a)&nbsp;[[Source code|code]] used to do the actual printing and (b)&nbsp;[[data]] that represents the textual form of the code. The code functions by using the data to print the code (which makes sense since the data represents the textual form of the code), but it also uses the data, processed in a simple way, to print the textual representation of the data itself.
In general, the method used to create a quine in any programming language is to have, within the program, two pieces: (a)&nbsp;[[Source code|code]] used to do the actual printing and (b)&nbsp;[[data]] that represents the textual form of the code. The code functions by using the data to print the code (which makes sense since the data represents the textual form of the code), but it also uses the data, processed in a simple way, to print the textual representation of the data itself.


Here are three small examples in Python 3:
Here are four small examples in Python3:
<syntaxhighlight lang="python3">a='a=%s%s%s;print(a%%(chr(39),a,chr(39)))';print(a%(chr(39),a,chr(39)))
<syntaxhighlight lang="python3">
# Example A. chr(39) == "'".
a = 'a = {}{}{}; print(a.format(chr(39), a, chr(39)))'; print(a.format(chr(39), a, chr(39)))
b='b={}{}{};print(b.format(chr(39),b,chr(39)))';print(b.format(chr(39),b,chr(39)))
c='c=%r;print(c%%c)';print(c%c)
#note that %r will quote automatically
</syntaxhighlight>
</syntaxhighlight>
<syntaxhighlight lang="python3">
# Example B. chr(39) == "'".
b = 'b = %s%s%s; print(b %% (chr(39), b, chr(39)))'; print(b % (chr(39), b, chr(39)))
</syntaxhighlight>
<syntaxhighlight lang="python3">
# Example C. %r will quote automatically.
c = 'c = %r; print(c %% c)'; print(c % c)
</syntaxhighlight><syntaxhighlight lang="python3">
file = open("temp.py", "r")

try:
temp_python = open("temp1.py", "w")
except FileNotFoundError:
temp_python = open("temp1.py", "w")


for i in file:
The following [[Java (programming language)|Java]] code demonstrates the basic structure of a quine.
temp_python.writelines(i)
// in this program(code) of quine, the output is an file output
</syntaxhighlight>The following [[Java (programming language)|Java]] code demonstrates the basic structure of a quine.
<syntaxhighlight lang="java">
<syntaxhighlight lang="java">
public class Quine
public class Quine
Line 70: Line 89:
" ",
" ",
" };",
" };",
" for(int i = 0; i < 6; i++) // Print opening code",
" for (int i = 0; i < 6; i++) // Print opening code",
" System.out.println(l[i]);",
" System.out.println(l[i]);",
" for(int i = 0; i < l.length; i++) // Print string array",
" for (int i = 0; i < l.length; i++) // Print string array",
" System.out.println(l[6] + q + l[i] + q + ',');",
" System.out.println(l[6] + q + l[i] + q + ',');",
" for(int i = 7; i < l.length; i++) // Print this code",
" for (int i = 7; i < l.length; i++) // Print this code",
" System.out.println(l[i]);",
" System.out.println(l[i]);",
" }",
" }",
"}",
"}",
};
};
for(int i = 0; i < 6; i++) // Print opening code
for (int i = 0; i < 6; i++) // Print opening code
System.out.println(l[i]);
System.out.println(l[i]);
for(int i = 0; i < l.length; i++) // Print string array
for (int i = 0; i < l.length; i++) // Print string array
System.out.println(l[6] + q + l[i] + q + ',');
System.out.println(l[6] + q + l[i] + q + ',');
for(int i = 7; i < l.length; i++) // Print this code
for (int i = 7; i < l.length; i++) // Print this code
System.out.println(l[i]);
System.out.println(l[i]);
}
}
Line 89: Line 108:
The source code contains a string array of itself, which is output twice, once inside quotation marks.
The source code contains a string array of itself, which is output twice, once inside quotation marks.


This code was adapted from an original post from c2.com, where the author, Jason Wilson, posted it as a minimalistic version of a Quine, without Java comments.<ref>http://wiki.c2.com/?QuineProgram</ref>
This code was adapted from an original post from c2.com, where the author, Jason Wilson, posted it as a minimalistic version of a Quine, without Java comments.<ref>{{cite web |url=http://wiki.c2.com/?QuineProgram |title=Quine Program |website=wiki.c2.com}}</ref>


Thanks to new [https://openjdk.java.net/jeps/378 text blocks] feature in Java 15 (or newer), a more readable and simpler version is possible:<ref>{{Cite web|url=https://gist.github.com/destan/c0db5a237e9875a56141403aaa6cb9c7|title=Simple Java quine, self replicating (Self copying) Java code, with text blocks. This code can be run with Java 15+ or Java 13+ with special flags. License is public domain, no rights reserved}}</ref>
Thanks to new [https://openjdk.java.net/jeps/378 text blocks] feature in Java 15 (or newer), a more readable and simpler version is possible:<ref>{{Cite web|url=https://gist.github.com/destan/c0db5a237e9875a56141403aaa6cb9c7|title=Simple Java quine, self replicating (Self copying) Java code, with text blocks. This code can be run with Java 15+ or Java 13+ with special flags. License is public domain, no rights reserved}}</ref>


<syntaxhighlight lang="text">
<syntaxhighlight lang="java">
public class Quine {
public class Quine {
public static void main(String[] args) {
public static void main(String[] args) {
Line 130: Line 149:


==== Self-evaluation ====
==== Self-evaluation ====
In many functional languages, including [[Scheme (programming language)|Scheme]] and other [[Lisp (programming language)|Lisps]], and interactive languages such as [[APL (programming language)|APL]], numbers are self-evaluating. In [[TI-BASIC]], if the last line of a program returns a value, the returned value is displayed on the screen. Therefore, in such languages a program consisting of only a single digit results in a 1-byte quine. Since such code does not ''construct'' itself, this is often considered cheating.
In many functional languages, including [[Scheme (programming language)|Scheme]] and other [[Lisp (programming language)|Lisps]], and interactive languages such as [[APL (programming language)|APL]], numbers are self-evaluating. In [[TI-BASIC]], if the last line of a program returns a value, the returned value is displayed on the screen. Therefore, in such languages a program consisting of only a single digit results in a 1-byte quine. Since such code does not ''construct'' itself, this is often considered cheating.


<syntaxhighlight lang="basic">
<syntaxhighlight lang="basic">
Line 136: Line 155:
</syntaxhighlight>
</syntaxhighlight>


==== Empty quines ====
Another such example involves the interactive Python feature where the underscore symbol is assigned the value of the previous line.

<syntaxhighlight lang="python">
'%r\nprint(_%%_)'
print(_%_)
</syntaxhighlight>

In some languages, particularly [[scripting language]]s but also [[C (programming language)|C]], an empty source file is a fixed point of the language, being a valid program that produces no output.{{efn|1=Examples include [[Bash (Unix shell)|Bash]], [[Perl]], and [[Python (programming language)|Python]]}} Such an empty program, submitted as "the world's smallest self reproducing program", once won the "worst abuse of the rules" prize in the [[International Obfuscated C Code Contest]].<ref>{{cite web |url = http://www0.us.ioccc.org/1994/smr.hint |title = IOCCC 1994 Worst Abuse of the Rules |archive-url=https://web.archive.org/web/20201112015540/http://www0.us.ioccc.org/1994/smr.hint |archive-date=12 November 2020 |url-status=dead}}</ref> The program was not actually compiled, but used <code>cp</code> to copy the file into another file, which could be executed to print nothing.<ref>{{cite web |title=Makefile |url=http://www0.us.ioccc.org/1994/Makefile |website=IOCCC.org |access-date=4 April 2019 |archive-date=23 April 2019 |archive-url=https://web.archive.org/web/20190423002150/http://www0.us.ioccc.org/1994/Makefile |url-status=dead }}</ref>
In some languages, particularly [[scripting language]]s but also [[C (programming language)|C]], an empty source file is a fixed point of the language, being a valid program that produces no output.{{efn|1=Examples include [[Bash (Unix shell)|Bash]], [[Perl]], and [[Python (programming language)|Python]]}} Such an empty program, submitted as "the world's smallest self reproducing program", once won the "worst abuse of the rules" prize in the [[International Obfuscated C Code Contest]].<ref>{{cite web |url = http://www0.us.ioccc.org/1994/smr.hint |title = IOCCC 1994 Worst Abuse of the Rules |archive-url=https://web.archive.org/web/20201112015540/http://www0.us.ioccc.org/1994/smr.hint |archive-date=12 November 2020 |url-status=dead}}</ref> The program was not actually compiled, but used <code>cp</code> to copy the file into another file, which could be executed to print nothing.<ref>{{cite web |title=Makefile |url=http://www0.us.ioccc.org/1994/Makefile |website=IOCCC.org |access-date=4 April 2019 |archive-date=23 April 2019 |archive-url=https://web.archive.org/web/20190423002150/http://www0.us.ioccc.org/1994/Makefile |url-status=dead }}</ref>

Other questionable techniques include making use of compiler messages; for example, in the [[GW-BASIC]] environment, entering "Syntax Error" will cause the interpreter to respond with "Syntax Error".


==== Source code inspection ====
==== Source code inspection ====
Line 160: Line 171:
#!/bin/cat
#!/bin/cat
</syntaxhighlight>
</syntaxhighlight>

Other questionable techniques include making use of compiler messages; for example, in the [[GW-BASIC]] environment, entering "Syntax Error" will cause the interpreter to respond with "Syntax Error".


==Ouroboros programs==
==Ouroboros programs==
Line 166: Line 179:
===Example===
===Example===
This Java program outputs the source for a C++ program that outputs the original Java code.
This Java program outputs the source for a C++ program that outputs the original Java code.
<!--
<div style="width: 50%; overflow: auto; float: right;" >
NOTE TO EDITORS: The following code is very fragile. If you edit it, be very careful not to break it -- verify that the output of the Java program is identical to the C++ program, and that the output of the C++ program is identical to the Java program.
-->
<div style="width: 49%; overflow: auto; float: right; padding-left: 1%;" >
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
#include <iostream>
#include <iostream>
Line 204: Line 220:
" };",
" };",
" for(int i = 2; i <= 9; i++)",
" for(int i = 2; i <= 9; i++)",
" System.out.println( l[i] );",
" System.out.println(l[i]);",
" for(int i = 0; i < l.length; i++)",
" for(int i = 0; i < l.length; i++)",
" System.out.println(l[0] + q + l[i] + q + ',');",
" System.out.println(l[0] + q + l[i] + q + ',');",
Line 220: Line 236:
return 0;
return 0;
}</syntaxhighlight>
}</syntaxhighlight>
</div><div style="width: 49%; overflow: auto; float: left;" >
</div><div style="width: 49%; overflow: auto; float: left; padding-right: 1%;" >
<syntaxhighlight lang="java">public class Quine
<syntaxhighlight lang="java">public class Quine
{
{
Line 246: Line 262:
" return 0;",
" return 0;",
"}",
"}",
"=============<<<<<<<< Java Code >>>>>>>>==========",
"=============<<<<<<<< Java Code >>>>>>>>=============",
"public class Quine",
"public class Quine",
"{",
"{",
" public static void main( String[] args )",
" public static void main(String[] args)",
" {",
" {",
" char q = 34;",
" char q = 34;",
Line 257: Line 273:
" System.out.println(l[i]);",
" System.out.println(l[i]);",
" for(int i = 0; i < l.length; i++)",
" for(int i = 0; i < l.length; i++)",
" System.out.println( l[0] + q + l[i] + q + ',' );",
" System.out.println(l[0] + q + l[i] + q + ',');",
" for(int i = 10; i <= 18; i++))",
" for(int i = 10; i <= 18; i++)",
" System.out.println(l[i]);",
" System.out.println(l[i]);",
" }",
" }",
Line 266: Line 282:
System.out.println(l[i]);
System.out.println(l[i]);
for(int i = 0; i < l.length; i++)
for(int i = 0; i < l.length; i++)
System.out.println( l[0] + q + l[i] + q + ',' );
System.out.println(l[0] + q + l[i] + q + ',');
for(int i = 10; i <= 18; i++)
for(int i = 10; i <= 18; i++)
System.out.println(l[i]);
System.out.println(l[i]);
}

}
}</syntaxhighlight></div>
}</syntaxhighlight></div>


Line 327: Line 342:
|author = Ku-ma-me
|author = Ku-ma-me
|date = 22 September 2009
|date = 22 September 2009
}}{{Dead link|date=May 2022}}</ref>
|access-date = 17 March 2011
|archive-date = 29 August 2011
|archive-url = https://web.archive.org/web/20110829204605/http://asiajin.com/blog/2009/09/22/uroboros-programming-with-11-programming-languages/
|url-status = dead
}}</ref>
* [[Ruby (programming language)|Ruby]] → [[Scala (programming language)|Scala]] → [[Scheme (programming language)|Scheme]] → [[Scilab]] → [[Bash (Unix shell)|Shell (bash)]] → [[S (programming language)|S-Lang]] → [[Smalltalk]] → [[Squirrel (programming language)|Squirrel3]] → [[Standard ML]] → ... → [[Rexx]] (128 (and formerly 50) programming languages)<ref>{{cite web
* [[Ruby (programming language)|Ruby]] → [[Scala (programming language)|Scala]] → [[Scheme (programming language)|Scheme]] → [[Scilab]] → [[Bash (Unix shell)|Shell (bash)]] → [[S (programming language)|S-Lang]] → [[Smalltalk]] → [[Squirrel (programming language)|Squirrel3]] → [[Standard ML]] → ... → [[Rexx]] (128 (and formerly 50) programming languages)<ref>{{cite web
|url = https://github.com/mame/quine-relay
|url = https://github.com/mame/quine-relay
Line 352: Line 371:


<blockquote>
<blockquote>
"A multiquine is a set of r different programs (in r different languages – without this condition we could take them all equal to a single quine), each of which is able to print any of the r programs (including itself) according to the command line argument it is passed. (Note that cheating is not allowed: the command line arguments must not be too long – passing the full text of a program is considered cheating)."
"A multiquine is a set of r different programs (in r different languages – without this condition we could take them all equal to a single quine), each of which is able to print any of the r programs (including itself) according to the command line argument it is passed. (Cheating is not allowed: the command line arguments must not be too long – passing the full text of a program is considered cheating)."
</blockquote>
</blockquote>


Line 378: Line 397:
|date = 21 May 2021
|date = 21 May 2021
}}</ref>
}}</ref>

==Polyglot==

Similar to, but unlike a multiquine, a [[polyglot (computing)|polyglot]] program is a computer program or script written in a valid form of multiple programming languages or file formats by combining their syntax. A polyglot program is not required to have a self-reproducing quality, although a polyglot program can also be a quine in one or more of its possible ways to execute.

Unlike quines and multiquines, polyglot programs are not guaranteed to exist between arbitrary sets of languages as a result of Kleene's recursion theorem, because they rely on the interplay between the syntaxes, and not a provable property that one can always be embedded within another.


=={{Anchor|RADIATION}}Radiation-hardened==
=={{Anchor|RADIATION}}Radiation-hardened==
Line 407: Line 432:
eval eval"[eval||=9,instance_eval||=9].max_by{|s|s.size}#"##"
eval eval"[eval||=9,instance_eval||=9].max_by{|s|s.size}#"##"
</syntaxhighlight>
</syntaxhighlight>

== Automatic generation ==
Using [[relational programming]] techniques, it is possible to generate quines automatically by transforming the interpreter (or equivalently, the compiler and runtime) of a language into a relational program, and then solving for a [[fixed point (mathematics)|fixed point]].<ref>{{Cite journal |last=Byrd |first=William E. |last2=Holk |first2=Eric |last3=Friedman |first3=Daniel P. |date=2012-09-09 |title=miniKanren, live and untagged: quine generation via relational interpreters (programming pearl) |url=http://webyrd.net/quines/quines.pdf |journal=Proceedings of the 2012 Annual Workshop on Scheme and Functional Programming |series=Scheme '12 |location=New York, NY, USA |publisher=Association for Computing Machinery |pages=8–29 |doi=10.1145/2661103.2661105 |isbn=978-1-4503-1895-2}}</ref>


==See also==
==See also==
{{Portal|Computer programming}}
{{Portal|Computer programming}}
{{cols}}
{{cols}}
*[[Diagonal lemma]]
* [[Diagonal lemma]]
*[[Droste effect]]
* [[Droste effect]]
*[[Fixed point combinator]]
* [[Fixed point combinator]]
*[[Self-modifying code]]
* [[Self-modifying code]]
*[[Self-interpreter]]
* [[Self-interpreter]]
*[[Self-replicating machine]]
* [[Self-replicating machine]]
*[[Self-replication]]
* [[Self-replication]]
*[[Self-relocation]]
* [[Self-relocation]]
*[[Tupper's self-referential formula]]
* [[TiddlyWiki]]
* [[Tupper's self-referential formula]]
*[[Programming languages]]
* [[Programming languages]]
*[[Quine's paradox]]
* [[Quine's paradox]]
* [[Polyglot (computing)]]
{{colend}}
{{colend}}



Latest revision as of 13:29, 8 May 2024

A quine's output is exactly the same as its source code (the syntax highlighting demonstrated by the text editor in the upper half of the image does not affect the output of the quine).

A quine is a computer program that takes no input and produces a copy of its own source code as its only output. The standard terms for these programs in the computability theory and computer science literature are "self-replicating programs", "self-reproducing programs", and "self-copying programs".

A quine is a fixed point of an execution environment, when that environment is viewed as a function transforming programs into their outputs. Quines are possible in any Turing-complete programming language, as a direct consequence of Kleene's recursion theorem. For amusement, programmers sometimes attempt to develop the shortest possible quine in any given programming language.

Name[edit]

The name "quine" was coined by Douglas Hofstadter, in his popular science book Gödel, Escher, Bach, in honor of philosopher Willard Van Orman Quine (1908–2000), who made an extensive study of indirect self-reference, and in particular for the following paradox-producing expression, known as Quine's paradox:

"Yields falsehood when preceded by its quotation" yields falsehood when preceded by its quotation.

History[edit]

The idea of self-reproducing automata came from the dawn of computing, if not before. John von Neumann theorized about them in the 1940s. Later, Paul Bratley and Jean Millo's article "Computer Recreations: Self-Reproducing Automata" discussed them in 1972.[1] Bratley first became interested in self-reproducing programs after seeing the first known such program written in Atlas Autocode at Edinburgh in the 1960s by the University of Edinburgh lecturer and researcher Hamish Dewar.

The "download source" requirement of the GNU Affero General Public License is based on the idea of a quine.[2]

Examples[edit]

Constructive quines[edit]

In general, the method used to create a quine in any programming language is to have, within the program, two pieces: (a) code used to do the actual printing and (b) data that represents the textual form of the code. The code functions by using the data to print the code (which makes sense since the data represents the textual form of the code), but it also uses the data, processed in a simple way, to print the textual representation of the data itself.

Here are four small examples in Python3:

# Example A. chr(39) == "'".
a = 'a = {}{}{}; print(a.format(chr(39), a, chr(39)))'; print(a.format(chr(39), a, chr(39)))
# Example B. chr(39) == "'".
b = 'b = %s%s%s; print(b %% (chr(39), b, chr(39)))'; print(b % (chr(39), b, chr(39)))
# Example C. %r will quote automatically.
c = 'c = %r; print(c %% c)'; print(c % c)
file = open("temp.py", "r")

try:
    temp_python = open("temp1.py", "w")
except FileNotFoundError:
    temp_python = open("temp1.py", "w")

for i in file:
    temp_python.writelines(i)
    
// in this program(code) of quine, the output is an file output

The following Java code demonstrates the basic structure of a quine.

public class Quine
{
  public static void main(String[] args)
  {
    char q = 34;      // Quotation mark character
    String[] l = {    // Array of source code
    "public class Quine",
    "{",
    "  public static void main(String[] args)",
    "  {",
    "    char q = 34;      // Quotation mark character",
    "    String[] l = {    // Array of source code",
    "    ",
    "    };",
    "    for (int i = 0; i < 6; i++)           // Print opening code",
    "        System.out.println(l[i]);",
    "    for (int i = 0; i < l.length; i++)    // Print string array",
    "        System.out.println(l[6] + q + l[i] + q + ',');",
    "    for (int i = 7; i < l.length; i++)    // Print this code",
    "        System.out.println(l[i]);",
    "  }",
    "}",
    };
    for (int i = 0; i < 6; i++)           // Print opening code
        System.out.println(l[i]);
    for (int i = 0; i < l.length; i++)    // Print string array
        System.out.println(l[6] + q + l[i] + q + ',');
    for (int i = 7; i < l.length; i++)    // Print this code
        System.out.println(l[i]);
  }
}

The source code contains a string array of itself, which is output twice, once inside quotation marks.

This code was adapted from an original post from c2.com, where the author, Jason Wilson, posted it as a minimalistic version of a Quine, without Java comments.[3]

Thanks to new text blocks feature in Java 15 (or newer), a more readable and simpler version is possible:[4]

public class Quine {
	public static void main(String[] args) {
		String textBlockQuotes = new String(new char[]{'"', '"', '"'});
		char newLine = 10;
		String source = """
public class Quine {
	public static void main(String[] args) {
		String textBlockQuotes = new String(new char[]{'"', '"', '"'});
		char newLine = 10;
		String source = %s;
		System.out.print(source.formatted(textBlockQuotes + newLine + source + textBlockQuotes));
	}
}
""";
		System.out.print(source.formatted(textBlockQuotes + newLine + source + textBlockQuotes));
	}
}

Eval quines[edit]

Some programming languages have the ability to evaluate a string as a program. Quines can take advantage of this feature. For example, this Ruby quine:

eval s="print 'eval s=';p s"

Lua can do:

s="print(string.format('s=%c%s%c; load(s)()',34,s,34))"; load(s)()

In Python 3.8:

exec(s:='print("exec(s:=%r)"%s)')

"Cheating" quines[edit]

Self-evaluation[edit]

In many functional languages, including Scheme and other Lisps, and interactive languages such as APL, numbers are self-evaluating. In TI-BASIC, if the last line of a program returns a value, the returned value is displayed on the screen. Therefore, in such languages a program consisting of only a single digit results in a 1-byte quine. Since such code does not construct itself, this is often considered cheating.

1

Empty quines[edit]

In some languages, particularly scripting languages but also C, an empty source file is a fixed point of the language, being a valid program that produces no output.[a] Such an empty program, submitted as "the world's smallest self reproducing program", once won the "worst abuse of the rules" prize in the International Obfuscated C Code Contest.[5] The program was not actually compiled, but used cp to copy the file into another file, which could be executed to print nothing.[6]

Source code inspection[edit]

Quines, per definition, cannot receive any form of input, including reading a file, which means a quine is considered to be "cheating" if it looks at its own source code. The following shell script is not a quine:

#!/bin/sh
# Invalid quine.
# Reading the executed file from disk is cheating.
cat $0

A shorter variant, exploiting the behaviour of shebang directives:

#!/bin/cat

Other questionable techniques include making use of compiler messages; for example, in the GW-BASIC environment, entering "Syntax Error" will cause the interpreter to respond with "Syntax Error".

Ouroboros programs[edit]

The quine concept can be extended to multiple levels of recursion, giving rise to "ouroboros programs", or quine-relays. This should not be confused with multiquines.

Example[edit]

This Java program outputs the source for a C++ program that outputs the original Java code.

#include <iostream>
#include <string>
using namespace std;

int main(int argc, char* argv[])
{
    char q = 34;
    string l[] = {
    "    ",
    "=============<<<<<<<< C++ Code >>>>>>>>=============",
    "#include <iostream>",
    "#include <string>",
    "using namespace std;",
    "",
    "int main(int argc, char* argv[])",
    "{",
    "    char q = 34;",
    "    string l[] = {",
    "    };",
    "    for(int i = 20; i <= 25; i++)",
    "        cout << l[i] << endl;",
    "    for(int i = 0; i <= 34; i++)",
    "        cout << l[0] + q + l[i] + q + ',' << endl;",
    "    for(int i = 26; i <= 34; i++)",
    "        cout << l[i] << endl;",
    "    return 0;",
    "}",
    "=============<<<<<<<< Java Code >>>>>>>>=============",
    "public class Quine",
    "{",
    "  public static void main(String[] args)",
    "  {",
    "    char q = 34;",
    "    String[] l = {",
    "    };",
    "    for(int i = 2; i <= 9; i++)",
    "        System.out.println(l[i]);",
    "    for(int i = 0; i < l.length; i++)",
    "        System.out.println(l[0] + q + l[i] + q + ',');",
    "    for(int i = 10; i <= 18; i++)",
    "        System.out.println(l[i]);",
    "  }",
    "}",
    };
    for(int i = 20; i <= 25; i++)
        cout << l[i] << endl;
    for(int i = 0; i <= 34; i++)
        cout << l[0] + q + l[i] + q + ',' << endl;
    for(int i = 26; i <= 34; i++)
        cout << l[i] << endl;
    return 0;
}
public class Quine
{
  public static void main(String[] args)
  {
    char q = 34;
    String[] l = {
    "    ",
    "=============<<<<<<<< C++ Code >>>>>>>>=============",
    "#include <iostream>",
    "#include <string>",
    "using namespace std;",
    "",
    "int main(int argc, char* argv[])",
    "{",
    "    char q = 34;",
    "    string l[] = {",
    "    };",
    "    for(int i = 20; i <= 25; i++)",
    "        cout << l[i] << endl;",
    "    for(int i = 0; i <= 34; i++)",
    "        cout << l[0] + q + l[i] + q + ',' << endl;",
    "    for(int i = 26; i <= 34; i++)",
    "        cout << l[i] << endl;",
    "    return 0;",
    "}",
    "=============<<<<<<<< Java Code >>>>>>>>=============",
    "public class Quine",
    "{",
    "  public static void main(String[] args)",
    "  {",
    "    char q = 34;",
    "    String[] l = {",
    "    };",
    "    for(int i = 2; i <= 9; i++)",
    "        System.out.println(l[i]);",
    "    for(int i = 0; i < l.length; i++)",
    "        System.out.println(l[0] + q + l[i] + q + ',');",
    "    for(int i = 10; i <= 18; i++)",
    "        System.out.println(l[i]);",
    "  }",
    "}",
    };
    for(int i = 2; i <= 9; i++)
        System.out.println(l[i]);
    for(int i = 0; i < l.length; i++)
        System.out.println(l[0] + q + l[i] + q + ',');
    for(int i = 10; i <= 18; i++)
        System.out.println(l[i]);
  }
}

Such programs have been produced with various cycle lengths:

Multiquines[edit]

David Madore, creator of Unlambda, describes multiquines as follows:[16]

"A multiquine is a set of r different programs (in r different languages – without this condition we could take them all equal to a single quine), each of which is able to print any of the r programs (including itself) according to the command line argument it is passed. (Cheating is not allowed: the command line arguments must not be too long – passing the full text of a program is considered cheating)."

A multiquine consisting of 2 languages (or biquine) would be a program which:

  • When run, is a quine in language X.
  • When supplied with a user-defined command line argument, would print a second program in language Y.
  • Given the second program in language Y, when run normally, would also be a quine in language Y.
  • Given the second program in language Y, and supplied with a user-defined command line argument, would produce the original program in language X.

A biquine could then be seen as a set of two programs, both of which are able to print either of the two, depending on the command line argument supplied.

Theoretically, there is no limit on the number of languages in a multiquine. A 5-part multiquine (or pentaquine) has been produced with Python, Perl, C, NewLISP, and F#[17] and there is also a 25-language multiquine.[18]

Polyglot[edit]

Similar to, but unlike a multiquine, a polyglot program is a computer program or script written in a valid form of multiple programming languages or file formats by combining their syntax. A polyglot program is not required to have a self-reproducing quality, although a polyglot program can also be a quine in one or more of its possible ways to execute.

Unlike quines and multiquines, polyglot programs are not guaranteed to exist between arbitrary sets of languages as a result of Kleene's recursion theorem, because they rely on the interplay between the syntaxes, and not a provable property that one can always be embedded within another.

Radiation-hardened[edit]

A radiation-hardened quine is a quine that can have any single character removed and still produces the original program with no missing character. Of necessity, such quines are much more convoluted than ordinary quines, as is seen by the following example in Ruby:[19]

eval='eval$q=%q(puts %q(10210/#{1 1 if 1==21}}/.i rescue##/

1 1"[13,213].max_by{|s|s.size}#"##").gsub(/\d/){["=\47eval$q=%q(#$q)#\47##\47

",:eval,:instance_,"||=9"][eval$&]}
exit)#'##'

instance_eval='eval$q=%q(puts %q(10210/#{1 1 if 1==21}}/.i rescue##/

1 1"[13,213].max_by{|s|s.size}#"##").gsub(/\d/){["=\47eval$q=%q(#$q)#\47##\47

",:eval,:instance_,"||=9"][eval$&]}
exit)#'##'

/#{eval eval if eval==instance_eval}}/.i rescue##/

eval eval"[eval||=9,instance_eval||=9].max_by{|s|s.size}#"##"

Automatic generation[edit]

Using relational programming techniques, it is possible to generate quines automatically by transforming the interpreter (or equivalently, the compiler and runtime) of a language into a relational program, and then solving for a fixed point.[20]

See also[edit]

Notes[edit]

  1. ^ Examples include Bash, Perl, and Python

References[edit]

  1. ^ Bratley, Paul; Millo, Jean (1972). "Computer Recreations: Self-Reproducing Automata". Software: Practice and Experience. 2 (4): 397–400. doi:10.1002/spe.4380020411. S2CID 222194376.
  2. ^ Kuhn, Bradley M. (November 21, 2007). "stet and AGPLv3". Software Freedom Law Center. Archived from the original on March 15, 2008. Retrieved June 14, 2008.
  3. ^ "Quine Program". wiki.c2.com.
  4. ^ "Simple Java quine, self replicating (Self copying) Java code, with text blocks. This code can be run with Java 15+ or Java 13+ with special flags. License is public domain, no rights reserved".
  5. ^ "IOCCC 1994 Worst Abuse of the Rules". Archived from the original on 12 November 2020.
  6. ^ "Makefile". IOCCC.org. Archived from the original on 23 April 2019. Retrieved 4 April 2019.
  7. ^ Dan Piponi (5 February 2008). "A Third Order Quine in Three Languages".
  8. ^ Bruce Ediger. "Ask and ye shall receive: Self-replicating program that goes through three generations, Python, Bash, Perl". Archived from the original on 2011-02-23. Retrieved 2011-03-17.
  9. ^ b.m. (1 February 2011). "multiquine". Archived from the original on 2013-04-15.
  10. ^ Dan Piponi (30 January 2011). "Quine Central".
  11. ^ Ruslan Ibragimov (20 April 2013). "Quine Ruby -> Java -> C# -> Python" (in Russian). Archived from the original on 4 March 2016. Retrieved 20 April 2013.
  12. ^ Shinichiro Hamaji (10 November 2007). "Quine by shinh (C C++ Ruby Python PHP Perl)". (this one is also a polyglot)
  13. ^ Ku-ma-me (22 September 2009). "Uroboros Programming With 11 Programming Languages". Archived from the original on 29 August 2011. Retrieved 17 March 2011.
  14. ^ Yusuke Endoh (2 November 2021). "Quine Relay - An uroboros program with 100+ programming languages". GitHub.
  15. ^ Michael Wehar (10 November 2019). "C Prints JavaScript".
  16. ^ David Madore. "Quines (self-replicating programs)".
  17. ^ Rijnard van Tonder (14 January 2020). "Pentaquine - 5 part multiquine". GitHub.
  18. ^ Lu Wang (21 May 2021). "Quine Chameleon#Variants". GitHub.
  19. ^ Yusuke Endoh. "Radiation-hardened Quine". GitHub. Retrieved 2014-02-24.
  20. ^ Byrd, William E.; Holk, Eric; Friedman, Daniel P. (2012-09-09). "miniKanren, live and untagged: quine generation via relational interpreters (programming pearl)" (PDF). Proceedings of the 2012 Annual Workshop on Scheme and Functional Programming. Scheme '12. New York, NY, USA: Association for Computing Machinery: 8–29. doi:10.1145/2661103.2661105. ISBN 978-1-4503-1895-2.

Further reading[edit]

External links[edit]