为了纪念Stack Overflow的公开发布,导致堆栈溢出的最短代码是什么?任何语言的欢迎。
ETA:在这个问题上要清楚一点,因为我偶尔是Scheme用户:尾调用“递归”实际上是迭代,因此任何可以由像样的编译器相对简单地转换为迭代解决方案的解决方案都不会被算在内。:-P
ETA2:我现在选择了“最佳答案”。请参阅此帖子以了解基本原理。感谢所有贡献者!:-)
为了纪念Stack Overflow的公开发布,导致堆栈溢出的最短代码是什么?任何语言的欢迎。
ETA:在这个问题上要清楚一点,因为我偶尔是Scheme用户:尾调用“递归”实际上是迭代,因此任何可以由像样的编译器相对简单地转换为迭代解决方案的解决方案都不会被算在内。:-P
ETA2:我现在选择了“最佳答案”。请参阅此帖子以了解基本原理。感谢所有贡献者!:-)
Answers:
所有这些答案,没有Befunge吗?我敢打赌,这是所有这些中最短的解决方案:
1
不开玩笑。自己尝试:http : //www.quirkster.com/iano/js/befunge.html
编辑:我想我需要解释这一点。1操作数将1压入Befunge的内部堆栈,由于缺少其他任何条件,它在语言规则下处于循环状态。
使用提供的解释器,您最终-我的意思是最终-达到了一个点,在该点上,代表Befunge堆栈的Javascript数组变得太大,以至于浏览器无法重新分配。如果您有一个简单的Befunge解释器,且堆栈较小且有界(以下大多数语言都是这种情况),则此程序将更快地引起更明显的溢出。
"
它加载它环绕每两次,32号的79个副本,而不是数字1的2份
我目前最好的(在x86汇编中)是:
push eax
jmp short $-1
结果是3个字节的目标代码(50 EB FD
)。对于16位代码,这也是可能的:
call $
这也将导致3个字节(E8 FD FF
)。
overflow
PUSH
0000 0000 0000 0101
CALL overflow
1110 1100 0000 0000
0000 0000 0000 0000
但是,仅CALL会执行堆栈溢出:
CALL $
1110 1100 0000 0000
0000 0000 0000 0000
但是RCALL(相对调用)仍然较小(不是全局内存,因此不需要额外的2个字节):
RCALL $
1101 1000 0000 0000
因此,PIC18上最小的是一条指令,即16位(两个字节)。每个循环将花费2个指令周期。每个指令周期有4个时钟周期,您就有8个时钟周期。PIC18具有31级堆栈,因此在第32次循环之后,它将在256个时钟周期内使堆栈溢出。在64MHz下,您将在4微秒和2个字节内使堆栈溢出。
但是,PIC16F5x系列使用12位指令:
CALL $
1001 0000 0000
同样,每个循环两个指令周期,每个指令4个时钟,因此每个循环8个时钟周期。
但是,PIC16F5x具有两级堆栈,因此在第三个循环中,它将以24条指令溢出。在20MHz时,它将在1.2微秒和1.5个字节内溢出。
在英特尔4004有一个8位CALL指令:
CALL $
0101 0000
对于与ascii“ P”相对应的好奇。3级堆栈需要24个时钟周期,总共需要32.4微秒和1个字节。(除非您对4004进行超频-来吧,否则您就知道要这么做。)
它与befunge答案一样小,但是比当前解释器中运行的befunge代码快得多。
每个任务都需要正确的工具。符合SO Overflow语言,经过优化可产生堆栈溢出:
so
TeX:
\def~{~.}~
结果是:
!超出TeX容量,很抱歉[输入堆栈大小= 5000]。 〜->〜 。 〜->〜 。 〜->〜 。 〜->〜 。 〜->〜 。 〜->〜 。 ... <*> \ def〜{〜。}〜
胶乳:
\end\end
结果是:
!超出TeX容量,很抱歉[输入堆栈大小= 5000]。 \ end#1-> \ csname end#1 \ endcsname \ @checkend {#1} \在\ endgroup \ if @ e之后展开... <*> \ end \ end
~
处于活动状态,因此可以代替使用\a
。我偶然发现了LaTeX代码。:)
用英语讲:
recursion = n. See recursion.
BASIC中的以下内容如何:
10 GOSUB 10
(恐怕我没有BASIC解释器,这是一个猜测)。
GOSUB
,而不是一个GOTO
。由于它RETURN
是从哪里调用的,因此肯定使用了堆栈吗?
这是我的C贡献,重18个字符:
void o(){o();o();}
这是一个很多难以尾调用优化!:-P
使用窗口的名为“ s.bat”的批处理文件:
call s
Groovy:
main()
$ groovy stack.groovy:
Caught: java.lang.StackOverflowError
at stack.main(stack.groovy)
at stack.run(stack.groovy:1)
...
请告诉我首字母缩写“ GNU ”代表什么。
C-它不是最短的,但是没有递归。它也不是可移植的:它在Solaris上崩溃,但是某些alloca()实现可能会在此处返回错误(或调用malloc())。调用printf()是必要的。
#include <stdio.h>
#include <alloca.h>
#include <sys/resource.h>
int main(int argc, char *argv[]) {
struct rlimit rl = {0};
getrlimit(RLIMIT_STACK, &rl);
(void) alloca(rl.rlim_cur);
printf("Goodbye, world\n");
return 0;
}
尝试在一个汉堡上放4个以上的小馅饼。堆栈溢出。
Python:
so=lambda:so();so()
或者:
def so():so()
so()
如果Python优化了尾调用...:
o=lambda:map(o,o());o()
我在这篇文章之后选择“最佳答案”。但是首先,我想承认一些非常原始的贡献:
尽管我很喜欢上述内容,但是挑战在于打高尔夫球,为了公平起见,对于受访者来说,我必须为最短的代码(即Befunge参赛作品)授予“最佳答案”。我不相信任何人都可以击败它(尽管Konrad确实尝试过),所以恭喜Patrick!
看到大量的递归堆栈溢出解决方案,令我感到惊讶的是,截至目前,没有人提出Y组合器(有关入门知识,请参见Dick Gabriel的文章The Why of Y)。我有一个使用Y组合器的递归解决方案,以及aku的f(f(x))方法。:-)
((Y (lambda (f) (lambda (x) (f (f x))))) #f)
爪哇
Java解决方案的略短版本。
class X{public static void main(String[]a){main(a);}}