Quine 的题解
记住只在没有思路时使用题解,不要从它复制粘贴代码。请尊重题目和题解的作者。
在解题之前提交题解的代码会导致封禁。
在解题之前提交题解的代码会导致封禁。
作者:
概述
本题要求编写一个自产生程序(Quine),即程序不接受任何输入,输出自身源代码的完整副本。核心解法是利用字符串格式化占位符(如 Python 的 %r)或 C 语言的 printf 格式控制,将源代码本身嵌入模板,通过自引用实现复制。
分析
核心观察
自产生程序的关键在于构造一个字符串 s,使其包含程序主体的模板,并在模板中预留占位符来表示 s 自身的字面量。当用 s 填充占位符时,结果与源代码完全一致。
思路
在 Python 中,%r 格式化符可将对象转为带引号的字符串字面量。令 s = 's=%r;print(s%%s)',则 s % s 将 %r 替换为 repr(s),展开后与源代码相同。
在 C++ 中,可利用 printf 的格式串,将自身源代码分为三部分:前导文本、带引号的字符串主体、尾部文本。printf(s, 10, 34, s, 34) 通过 %c 插入换行符和双引号,实现自我复制。由于题目要求忽略全部空白字符(空格、换行、制表符和字面 \n),即使程序含换行也不影响比较。
具体示例
Python 程序:
s='s=%r;print(s%%s)';print(s%s)
执行后输出完全相同的字符串(忽略空白后相同)。
C++ 程序(基于 printf):
#include<stdio.h>
int main(){char*s="#include<stdio.h>%cint main(){char*s=%c%s%c;printf(s,10,34,s,34);}";printf(s,10,34,s,34);}
输出同样与源代码一致。
算法步骤
- 定义字符串模板
s,其中包含程序的主体,并用占位符标记需要插入自身字面量的位置。 - 对模板进行自格式化:将占位符替换为
s自身的字面量(Python 用%r,C++ 用%s配合printf)。 - 输出格式化后的结果,即为完整源代码。
复杂度分析
- 时间:
,其中
为源代码长度。
- 空间:
,用于存储模板和输出字符串。
实现注意事项
- Python 中必须用
%%转义字面百分号,否则会被视为格式符。 - C++ 版本使用
printf,需包含<stdio.h>或<cstdio>,并正确插入换行符(ASCII 10)和双引号(ASCII 34)。 - 空白字符(包括换行)在比较时被忽略,因此可任意安排换行,但建议保持简洁。
- 确保输出的引号、分号等符号与源代码一致,尤其是双引号需通过转义或 ASCII 码输出。
源代码
s='s=%r;print(s%%s)';print(s%s)
#include<stdio.h>
int main(){char*s="#include<stdio.h>%cint main(){char*s=%c%s%c;printf(s,10,34,s,34);}";printf(s,10,34,s,34);}
评论