导致堆栈溢出的最短代码是什么?
为了纪念Stack Overflow的公开发布,导致堆栈溢出的最短代码是什么?任何语言的欢迎。
ETA:在这个问题上,我们需要清楚一点,因为我偶尔是Scheme用户:尾调用"递归"实际上是迭代,因此任何可以由像样的编译器相对简单地转换为迭代解决方案的解决方案都不会被算在内。 :-P
ETA2:我现在选择了最佳答案;请参阅此帖子以了解基本原理。感谢所有贡献者! :-)
解决方案
回答
我目前最好的(在x86汇编中)是:
push eax jmp short $-1
这将导致3个字节的目标代码(" 50 EB FD")。对于16位代码,这也是可能的:
call $
这也将导致3个字节(" E8 FD FF")。
回答
C ++:
int overflow(int n) { return overflow(1); }
回答
C#:
public int Foo { get { return Foo; } }
回答
Python:
so=lambda:so();so()
或者:
def so():so() so()
如果Python优化了尾调用...:
o=lambda:map(o,o());o()
回答
PIC18:
overflow PUSH CALL overflow
回答
int main(){ int a = 20; return main(); }
回答
JavaScript:
function i(){ i(); } i();
C ++
使用功能指针:
int main(){ int (*f)() = &main; f(); }
回答
用英语讲:
recursion = n. See recursion.
回答
/* In C/C++ (second attempt) */ int main(){ int a = main() + 1; return a; }
回答
这是我的C贡献,重18个字符:
void o(){o();o();}
调用优化的难度要大得多! :-P
回答
C#,用20个字符完成(不包括空格):
int s(){ return s(); }
回答
CIL / MSIL:
loop: ldc.i4.0 br loop
目标代码:
16 2B FD
回答
我们也可以在C#.net中尝试
throw new StackOverflowException();
回答
BASIC中的以下内容如何:
10 GOSUB 10
(我恐怕没有BASIC解释器,这是一个猜测)。
回答
Nemerle:
这会使编译器崩溃并产生StackOverflowException:
def o(){[o()]}
回答
红宝石:
def s() s() end; s()
回答
我喜欢Cody的答案堆,所以这是我在C ++中的类似贡献:
template <int i> class Overflow { typedef typename Overflow<i + 1>::type type; }; typedef Overflow<0>::type Kaboom;
无论如何,这都不是代码高尔夫球场,但仍然有任何东西会导致元堆栈溢出! :-P
回答
Lisp
(defun x() (x)) (x)
回答
a{return a*a;};
编译:
gcc -D"a=main()" so.c
扩展为:
main() { return main()*main(); }
回答
虚假:
class Foo { public Foo() {new Foo(); } }
回答
Perl 12个字符:
$_=sub{&$_};&$_
用10个字符组成bash(函数中的空格很重要):
i(){ i;};i
回答
完整的Delphi程序。
program Project1; {$APPTYPE CONSOLE} uses SysUtils; begin raise EStackOverflow.Create('Stack Overflow'); end.
回答
号角:
Poke(0)
回答
Java(令人尴尬):
public class SO { private void killme() { killme(); } public static void main(String[] args) { new SO().killme(); } }
编辑
当然可以将其大大缩短:
class SO { public static void main(String[] a) { main(null); } }
回答
so.c中的15个字符:
main(){main();}
结果:
antti@blah:~$ gcc so.c -o so antti@blah:~$ ./so Segmentation fault (core dumped)
编辑:好的,它使用-Wall发出警告,并且不会因-O2引起堆栈溢出。但这有效!
回答
我试图在Erlang中做到这一点:
c(N)->c(N+1)+c(N-1). c(0).
自身的两次调用使内存使用量提高到O(n ^ 2)而不是O(n)。
但是,Erlang解释器似乎无法崩溃。
回答
JavaSript:
嬉皮士回答一行:
(function i(){ i(); })()
相同数量的字符,但没有新行:)
回答
递归是一顶旧帽子。这是相互递归。通过调用任一函数开始。
a() { b(); } b() { a(); }
PS:但是我们要的是最短的方法..不是最有创意的方法!
回答
Java(X.java的完整内容):
class X { public static void main(String[] args) { main(null); }}
考虑到所有语法糖,我想知道在Java中是否可以做得更短。任何人?
编辑:糟糕,我想念已经发布了几乎相同的解决方案。
编辑2:我会说,这是(从字符角度看)最短的
class X{public static void main(String[]a){main(null);}}
编辑3:感谢安德斯(Anders)指出null不是最佳参数,因此它做起来更短:
class X{public static void main(String[]a){main(a);}}
回答
在单元散点图上,没有堆栈溢出,因此不需要递归,我们只需擦除堆栈指针即可。
asm(" andi $ 1,$ 1,0");
回答
3个字节:
`
label: pusha jmp label
`
<强>更新
根据(旧的)英特尔(?)文档,这也是3个字节:
`
label: call label
`
回答
PHP递归只是为了好玩。我想象需要一个PHP解释器来解决这个问题,但是嘿,它会导致崩溃。
function a() { a(); } a();
回答
已经有一个perl,但这要短几个字符(9 vs 12),并且不会递归:)
s//*_=0/e
回答
GWBASIC输出...
OK 10 i=0 20 print i; 30 i=i+1 40 gosub 20 run 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 Out of memory in 30 Ok
没有太多的堆栈深度:-)
回答
//lang = C++... it's joke, of course //Pay attention how void StackOverflow(){printf("StackOverflow!");} int main() { StackOverflow(); //called StackOverflow, right? }
回答
F#
人们不断问:" Fuseful有什么用?"
let rec f n = f (n)
性能优化的版本(将更快地失败:))
let rec f n = f (f(n))
回答
在E2上的无限循环中,我有这些列表,仅在标题中显示为"堆栈溢出"。
我认为最短的是
[dx]dx
在直流。在False中可能有一个更短的解决方案。
编辑:显然这不起作用...至少在GNU dc上。也许是在BSD版本上。
回答
红宝石:
def i()i()end;i()
(17个字符)
回答
在Lua:
function f()return 1+f()end f()
我们必须对递归调用的结果做些事情,否则尾部调用优化将使其永远循环。弱于打高尔夫,但很高兴!
我猜这和冗长的关键字意味着Lua不会很快赢得代码高尔夫。
回答
批处理程序称为call.cmd;
呼叫call.cmd
****** B A T C H R E C U R S I O N exceeds STACK limits ****** Recursion Count=1240, Stack Usage=90 percent ****** B A T C H PROCESSING IS A B O R T E D ******
回答
Perl的10个字符
sub x{&x}x
最终耗尽所有可用内存。
回答
MS-DOS批处理:
copy CON so.bat so.bat ^Z so.bat
回答
爪哇
Java解决方案的略短版本。
class X{public static void main(String[]a){main(a);}}
回答
在Scheme中,这将导致解释器的内存不足:
(define (x) ((x))) (x)
回答
包含换行符的10个字符的Shell脚本解决方案:
好吧,如果我们考虑生成一个新的进程作为构造一个新的堆栈框架,那么从技术上讲不是堆栈溢出,而是从逻辑上讲。
#!sh ./so
结果:
antti@blah:~$ ./so [disconnected]
哎呀注意:请勿在家中尝试
回答
在空白中,我认为:
它可能不会显示。 :/
回答
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; }
回答
具有27个非空白字符的C包括该呼叫。
Action a = null; a = () => a(); a();
回答
xor esp, esp ret
回答
电源外壳
$f={&$f};&$f
"脚本由于通话深度溢出而失败。通话深度达到1001,最大为1000。"
回答
阅读此行,然后说两次。
回答
bash:仅一个进程
\#!/bin/bash of() { of; } of
回答
Ruby,到目前为止比其他的要短:
def a;a;end;a
(13个字符)
回答
几乎任何外壳:
shmain()
(5个字符,仅在从文件运行时有效)
回答
尝试在一个汉堡上放4个以上的小馅饼。堆栈溢出。
回答
Groovy:
Caught: java.lang.StackOverflowError at stack.main(stack.groovy) at stack.run(stack.groovy:1) ...
$ groovy stack.groovy:
push cs push $-1 ret
回答
16位asm中的五个字节将导致堆栈溢出。
call $
回答
使用汇编语言(x86处理器,16或者32位模式):
int main( ) { return main( ); }
这将产生:
- 在32位模式下:0xe8; 0xfb; 0xff; 0xff; 0xff
- 在16位模式下:0xe8; 0xfd; 0xff
在C / C ++中:
rst 00
回答
Z-80汇编器-在内存位置0x0000处:
eval(i='eval(i)');
一个字节-0xC7-无穷循环,将当前PC推入堆栈并跳转到地址0x0000。
回答
Java脚本
要修剪更多的字符,并让自己离开更多的软件商店,让我们开始:
let x = x print x
回答
Haskell:
<cfinclude template="#ListLast(CGI.SCRIPT_NAME, "/\")#">
回答
好吧,还没有人提到Coldfusion,所以...
Function StackOverflow() As Integer Return StackOverflow() End Function
那应该做的。
回答
VB.Net
proc a {} a
回答
TCL:
proc a {} "a;a"
我没有可以执行尾递归的tclsh解释器,但是这可能愚弄这样的事情:
: a 1 recurse ; a
回答
向前:
: a 1 recurse ; a *the terminal*:1: Return stack overflow : a 1 recurse ; a ^ Backtrace:
在gforth
解释器内部:
<? require(__FILE__);
在Power Mac G4的"打开固件"提示符下,这只会挂起计算机。 :)
回答
糟糕,我不知道,我从未写过导致堆栈溢出的代码;)
回答
另一个PHP示例:
org 0 Loop nop jsr Loop
回答
为了获得乐趣,我不得不查找Motorolla HC11组件:
int x[100000000000];
回答
序言
p :-p。
= 5个字符
然后启动它并查询p
我认为这很小,并且在序言中用完了堆栈。
在swi prolog中仅对变量的查询将产生:
?X。
%... 1,000,000 ............ 10,000,000年后
%
%>> 42 <<(最新版本提出了问题)
这是另一个bash fork炸弹:
:(){:|:&}; ::
回答
作为C函数中的局部变量:
setTimeout(1, function() {while(1) a=1;});
回答
不是很短,但是有效! (JavaScript)
class _{static void Main(){Main();}}
回答
C#
1
请注意,我的是一个可编译程序,而不仅仅是一个函数。我还删除了多余的空格。
为了天赋,我将班级名称尽量缩小。
回答
所有这些答案,没有Befunge吗?我敢打赌,这是所有这些中最短的解决方案:
:
不开玩笑。自己尝试:http://www.quirkster.com/iano/js/befunge.html
编辑:我想我需要解释这一点。 1操作数将1压入Befunge的内部堆栈,并且由于缺少其他任何条件,它在语言规则下处于循环状态。
使用提供的解释器,我们最终-我的意思是最终-达到了一个点,在这个点上,代表Befunge堆栈的Javascript数组变得太大,浏览器无法重新分配。如果我们有一个简单的Befunge解释器,且堆栈较小且有界(如下面的大多数语言所示),则此程序会更快地引起更明显的溢出。
回答
除非存在一种空程序导致堆栈溢出的语言,否则以下内容应尽可能短。
Befunge:
:(){ :|:& };:
一遍又一遍地复制顶部堆栈的值。
编辑:
帕特里克的更好。用1s填充堆栈比用0s填充堆栈更好,因为解释器可以优化将0s作为空操作推入空堆栈。
回答
我认为这是我从未玩过的作弊行为;)但是,这里
8086汇编程序:
org Int3VectorAdrress;这是作弊吗?
诠释3
1个字节或者5个字符生成代码,怎么说呢?
回答
如果我们将调用框架视为一个进程,并将堆栈视为Unix计算机,则可以将fork炸弹视为一个并行程序,以创建堆栈溢出条件。试试这个13个字符的bash号。无需保存到文件。
class Overflow def initialize Overflow.new end end Overflow.new
回答
Ruby,尽管还不算短:
\def~{~.}~
回答
TeX:
! TeX capacity exceeded, sorry [input stack size=5000]. ~->~ . ~->~ . ~->~ . ~->~ . ~->~ . ~->~ . ... <*> \def~{~.}~
结果是:
\end\end
乳胶:
! TeX capacity exceeded, sorry [input stack size=5000]. \end #1->\csname end#1 \endcsname \@checkend {#1}\expandafter \endgroup \if@e... <*> \end\end
结果是:
enum A{B.values()} enum B{A.values()}
回答
我认为这可以在Java中使用(尝试):
static void Main(){Main();}
应该在静态初始化中溢出,甚至在由于缺少main(String [])而有机会失败之前就应该溢出。
回答
不会是最短的,但是我必须尝试一下... C#
string [] f =新的string [0]; Main(f);
短一点
Person JeffAtwood; Person JoelSpolsky; JeffAtwood.TalkTo(JoelSpolsky);
回答
call s
希望没有尾递归!
回答
使用Window的名为" s.bat"的批处理文件:
static void Main() { Main(); }
回答
在C#中,这将创建一个stackoverflow ...
mov sp,0
回答
为什么不
%!PS /increase {1 add} def 1 increase (so.ps) run
(堆栈长大)
回答
在名为so.ps的PostScript文件中,将导致execstackoverflow
/eval $L
回答
在Irssi(基于终端的IRC客户端,不是"真的"是一种编程语言)中,$ L表示当前命令行。因此,我们可能会导致堆栈溢出("达到最大递归限制"):
so
回答
每个任务都需要正确的工具。符合SO Overflow语言,经过优化可产生堆栈溢出:
(a=lambda{a.call}).call
回答
这是另一个Ruby答案,该答案使用lambda:
((Y (lambda (f) (lambda (x) (f (f x))))) #f)
回答
这篇文章之后,我正在选择最佳答案。但首先,我要感谢一些非常原始的贡献:
- 阿库的。每个人都探索一种导致堆栈溢出的新方法。做f(x)的想法? f(f(x))是我将在下面的下一篇文章中探讨的内容。 :-)
- Cody的代码为Nemerle编译器带来了堆栈溢出。
- 而且(有点勉强),GateKiller的问题是引发堆栈溢出异常。 :-P
尽管我很喜欢上述内容,但是挑战在于打高尔夫球,为了公平起见,对于受访者来说,我必须为最短的代码(即Befunge参赛作品)授予最佳答案。我不相信任何人都能击败它(尽管Konrad确实尝试过),所以恭喜Patrick!
看到大量的递归堆栈溢出解决方案,令我感到惊讶的是,截至目前,没有人提出Y组合器(请参阅Dick Gabriel的文章The Why of Y,了解入门知识)。我有一个使用Y组合器以及aku的f(f(x))方法的递归解决方案。 :-)
(function() { arguments.callee() })()
回答
JavaScript中的另一个:
Public Property Let x(ByVal y As Long) x = y End Property Private Sub Class_Initialize() x = 0 End Sub
回答
Vb6
main(){main()}
回答
可以编译K&R C中的简短解决方案:
((lambda (x) (x x)) (lambda (x) (x x)))
14字节
回答
这是Scheme中另一个有趣的内容:
var i=[]; i[i.push(i)]=i; trace(i);
回答
http://www.google.com/search?q=google.com
回答
动作3:所有操作都由数组完成...
S (K (S I I)) (S (S (K S) K) (K (S I I)))
也许不是最小的,但我认为它很可爱。特别是push方法会返回新的数组长度!
回答
作为对Y组合器评论的回应,我不妨通过SKI演算中的Y组合器:
run()
我不知道任何SKI解释器,但我曾经在一个小时左右的动作脚本中编写了一个图形化的解释器。如果有兴趣,我会乐意发帖(尽管我从未使版式工作得非常有效)
在这里阅读有关它的所有信息:。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
http://en.wikipedia.org/wiki/SKI_combinator_calculus
回答
在x86汇编中,在中断处理程序的内存中的位置放置一个0除指令,以将其除以0!
回答
Groovy(5B):
`echo @call b.cmd > b.cmd & b`
回答
在perl中:
p :- p, q. :- p.
实际上,这将与支持backquote-command语法并将其自身名称存储在$ 0中的任何shell一起使用。
回答
错误的:
[1] [1]#
(False是一种堆栈语言:是一个while循环,需要2个闭包,一个条件和一个body。body是导致溢出的那个)。
回答
CMD溢出一行
Redmond.Microsoft.Core.Windows.Start()
回答
序言
在咨询时,该程序会使SWI-Prolog和Sicstus Prolog崩溃。
overflow PUSH 0000 0000 0000 0101 CALL overflow 1110 1100 0000 0000 0000 0000 0000 0000
回答
CALL $ 1110 1100 0000 0000 0000 0000 0000 0000
回答
PIC18
TK给出的PIC18答案产生以下指令(二进制):
RCALL $ 1101 1000 0000 0000
但是,仅CALL会执行堆栈溢出:
CALL $ 1001 0000 0000
较小,更快的PIC18
但是RCALL(相对调用)仍然较小(不是全局内存,因此不需要额外的2个字节):
CALL $ 0101 0000
因此,PIC18上最小的是一条指令,即16位(两个字节)。每个循环将花费2个指令周期。每个指令周期有4个时钟周期,我们就有8个时钟周期。 PIC18具有31级堆栈,因此在第32次循环之后,它将在256个时钟周期内使堆栈溢出。在64MHz下,我们将在4微秒和2字节的时间内使堆栈溢出。
PIC16F5x(甚至更小,更快)
但是,PIC16F5x系列使用12位指令:
(defun f () (1+ (f)))
同样,每个循环两个指令周期,每个指令4个时钟,因此每个循环8个时钟周期。
但是,PIC16F5x具有两级堆栈,因此在第三个循环中,它将以24条指令溢出。在20MHz时,它将在1.2微秒和1.5字节内溢出。
英特尔4004
英特尔4004具有8位调用子例程指令:
fix (1+)
对于与ascii" P"相对应的好奇。 3级堆栈需要24个时钟周期,总共需要32.4微秒和1个字节。 (除非我们对4004进行超频,否则我们就知道要这么做。)
它与befunge答案一样小,但是比当前解释器中运行的befunge代码快得多。
回答
不能通过尾部调用来破坏尾部调用优化。在普通Lisp中:
fix f = (let x = f(x) in x)
回答
在Haskell
fix (1+)
这试图找到(1+)函数(n n + 1
)的固定点。该修复程序的实现是
(1+) ((1+) ((1+) ...))
所以
fix (+1)
变成
class C(int i) { C!(i+1) c; } C!(1) c;
注意
_asm t: call t;
只是循环。
回答
D中的元问题:
function c()c()end;
编译时间堆栈溢出
回答
a: make
回答
更好的lua解决方案:
$ make
将其粘贴到SciTE或者交互式命令提示符中,然后调用它。繁荣!
回答
请告诉我首字母缩写" GNU"代表什么。
回答
GNU make:
创建一个名为" Makefile"的文件,其内容如下:
b ## ties the winning entry with only one character (does not require end-of-line)
然后运行make:
$ ( PATH=$PATH:. ; b )
注意,必须使用制表符来抵消单词" make"。该文件为9个字符,包括2个行尾字符和1个制表符。
我想你可以用bash做类似的事情,但是有趣起来可能太容易了:
创建一个文件名" b",并将其标记为可执行文件(chmod + x b):
import sys sys.setrecursionlimit(sys.maxint) def so(): so() so()
现在使用
int main(void) { return main(); }
很难说这种方法在技术上是否会导致堆栈溢出,但是它的确建立了一个堆栈,该堆栈会一直增长,直到机器资源耗尽为止。使用GNU make这样做的好处是,我们可以观察它在构建和破坏堆栈时输出状态信息(假设我们在崩溃发生之前的某个时刻命中了^ C)。
回答
Python:
fib←{ ??0 1:? +/?¨?-1 2 }
回答
PHP是递归的缩写
回答
main = print $ x 1 where x y = x y + 1
回答
Dyalog APL
// v___v let rec f o = f(o);(o) // ['---'] // -"---"-
回答
Haskell:
real n(0) n(1)=0 end
回答
嘶哑溢出!
call main end
回答
Fortran,13和20个字符
class X{static{new X();}{new X();}}
或者
static { new X(); }
第二种情况是编译器相关的;对于GNU Fortran,将需要使用-fno-underscoring
进行编译。
(两者都包括必需的换行符)
回答
Java的:
{ new X(); }
实际上会导致堆栈溢出,从而初始化X类。在调用main()之前,JVM必须加载该类,并且在加载该类时,它将触发任何匿名静态代码块:
main(){ main(); }
如我们所见,它使用默认构造函数实例化X。 JVM甚至会在构造函数之前调用匿名代码块:
:a @call :a
这是递归的部分。
回答
let rec f l = f l@l;;
坦率和友善的C.对我来说很直观。
回答
另一个Windows Batch文件:
# f [0];; Stack overflow during evaluation (looping recursion?).
回答
OCaml
template<int n>struct f{f<n+1>a;};f<0>::a;
这个有点不同。堆栈上只有一个堆栈帧(因为它是尾递归的),但是它的输入一直在增长直到溢出堆栈。只需使用非空列表调用f
即可(在解释器提示处):
$ g++ test.cpp; test.cpp:1: error: template instantiation depth exceeds maximum of 500 (use -ftemplate-depth-NN to increase the maximum) instantiating ‘struct f<500>’ test.cpp:1: instantiated from ‘f<499>’ test.cpp:1: instantiated from ‘f<498>’ ......
回答
eval(t="eval(t)")
输出:
t="Execute(t)":Execute(t)
即使编译器遍历了模板,也会出现下一个错误:缺少" main"。
回答
JavaScript(17字节)
class A{{new A();}static{new A();}}
VB脚本(25字节)
Exception in thread "main" java.lang.StackOverflowError at A.<init>(A.java:1) ...... at A.<init>(A.java:1) Could not find the main class: A. Program will exit.
回答
Java:35个字符
我认为为时已晚,但我仍然会发表我的想法:
{/}loop
使用静态初始值设定项和实例初始值设定项功能。
这是我计算机上的输出(注意它显示了两个错误消息):
GS>{/}loop Error: /stackoverflow in --execute-- Operand stack: --nostringval-- Execution stack: %interp_exit .runexec2 --nostringval-- --nostringval-- --nostringval-- 2 %stopped_push --nostringval-- --nostringval-- %loop_continue 1753 2 3 %oparray_pop --nostringval-- --nostringval-- false 1 %stopped_push .runexec2 --nostringval-- --nostringval-- --nostringval-- 2 %stopped_push --nostringval-- --nostringval-- %loop_continue Dictionary stack: --dict:1150/1684(ro)(G)-- --dict:0/20(G)-- --dict:70/200(L)-- Current allocation mode is local Last OS error: 11 Current file position is 8
另请参阅:http://download.oracle.com/docs/cd/E17409_01/javase/tutorial/java/javaOO/initial.html
回答
[{/[aload 8 1 roll]cvx exec}aload 8 1 roll]cvx exec
在GhostScript中运行时,引发以下异常:
def a(x);x.gsub(/./){aclass Program { class StackOverflowExceptionOverflow : System.Exception { public StackOverflowExceptionOverflow() { throw new StackOverflowExceptionOverflow(); } } static void Main(string[] args) { throw new StackOverflowExceptionOverflow(); } }};end;a"x"
这是不使用变量(51个字符)的递归版本:
.org 1000 loop: call loop
回答
红宝石(再次):
+[>+]
已经有很多红宝石解决方案,但是我认为我会投入一个正则表达式以取得良好效果。
回答
C#
##代码##我意识到这不是最短的(甚至代码打高尔夫也不会接近短的任何地方),但是我无法忍受抛出一个异常,即在抛出异常时,它会终止运行时本身,并抛出一个stackoverflowexception。 ^^
回答
Z80汇编语言...
##代码##这将在位置1000处生成3个字节的代码....
1000 CD 00 10
回答
。
回答
即使它实际上没有堆栈...
brainf * ck 5个字符
##代码##