所以我在过去的八个小时里一直在使用Erlang,我花了两个人对着键盘敲击我试图弄清楚我的控制台一直在返回的异常错误。
我正在写一个骰子程序来学习erlang。我希望它能够通过erlang解释器从控制台调用。程序接受一些骰子,并且应该生成一个值列表。每个值应该在1到6之间。
我不会厌倦我为尝试解决问题(随机工程)而做出的几十个微观变化,但我会发布我的代码和错误。
来源:
-module(dice2).
-export([d6/1]).
d6(1) ->
random:uniform(6);
d6(Numdice) ->
Result = [],
d6(Numdice, [Result]).
d6(0, [Finalresult]) ->
{ok, [Finalresult]};
d6(Numdice, [Result]) ->
d6(Numdice - 1, [random:uniform(6) | Result]).
当我从我的控制台运行程序时......
dice2:d6(1).
...我得到一个像预期的一到六个之间的随机数。 但是,当我使用大于1的任何数字作为参数运行相同的函数时,我得到以下异常......
**异常错误:没有匹配dice2的函数子句:d6(1,[4 | 3])
...我知道我没有匹配参数的函数,但我不知道如何编写一个带有变量参数的函数,以及一个变量 number 的参数。
我尝试修改有问题的功能......
d6(Numdice, [Result]) ->
Newresult = [random:uniform(6) | Result],
d6(Numdice - 1, Newresult).
...但我的错误基本相同。有人知道这里发生了什么吗?
答案 0 :(得分:6)
这基本上是一种类型错误。当Result
是列表时,[Result]
是包含一个元素的列表。例如,如果您的函数有效,它将始终返回一个包含一个元素的列表:Finalresult
。
这就是发生的事情(使用==>
表示“减少到”):
d6(2) ==> %% Result == []
d6(2, [[]]) ==> %% Result == [], let's say random:uniform(6) gives us 3
d6(1, [3]) ==> %% Result == 3, let's say random:uniform(6) gives us 4
d6(0, [4|3]) ==> %% fails, since [Result] can only match one-element lists
据推测,您在第一次通话中不需要[[]]
,并且您不希望第三次通话中Result
为3。所以这应该解决它:
d6(Numdice) -> Result = [], d6(Numdice, Result). %% or just d6(Numdice, []).
d6(0, Finalresult) -> {ok, Finalresult};
d6(Numdice, Result) -> d6(Numdice - 1, [random:uniform(6) | Result]).
课程:如果语言是动态输入的,这并不意味着您可以避免使类型更正。相反,这意味着编译器无法帮助您尽可能地帮助您完成此任务。