BAR*_*BAR 1 memory heap erlang
可以在erlang中完成以下操作,并且不会因内存堆问题而导致崩溃吗?
loop() ->
receive
{drop, X} -> drop(X);
X -> handle(X)
end.
handle(X) ->
case X of
ok -> loop()
end.
drop(X) ->
case X of
ok -> loop()
end.
Run Code Online (Sandbox Code Playgroud)
尝试看看会发生什么很容易:
-module(loop).
-compile(export_all).
loop() ->
receive
{drop, X} -> drop(X);
after 1000 ->
erlang:display(catch erlang:error(noes)),
drop(ok)
end.
drop(X) ->
case X of
ok -> loop()
end.
Run Code Online (Sandbox Code Playgroud)
如果你运行loop:loop(),你会发现它确实没有增加堆栈.如果在调用drop(ok)或loop()之后添加1,则会看到堆栈在增长.
所以编译器发现它是一个尾调用并优化它,即使它不是一个递归的尾调用.