Function 在Erlang中,有没有办法创建空函数?

Function 在Erlang中,有没有办法创建空函数?,function,erlang,Function,Erlang,我正在编写一个Erlang函数,它可以打印到给定参数的每个偶数 到目前为止,我已经编写了具有如下防护的函数: printEven(I,N) when I < N -> if I rem 2 == 0 -> io:format("~p~n",[I]), printEven(I+1,N); I rem 2 == 1 -> printEven(I+1,N) end; printEven(I,N) -> io:format("Done").

我正在编写一个Erlang函数,它可以打印到给定参数的每个偶数

到目前为止,我已经编写了具有如下防护的函数:

printEven(I,N) when I < N ->
  if
    I rem 2 == 0 -> io:format("~p~n",[I]), printEven(I+1,N);
    I rem 2 == 1 -> printEven(I+1,N)
  end;
printEven(I,N) ->
   io:format("Done").
I
如果
I rem 2==0->io:format(“~p~n”,I]),print偶数(I+1,n);
I rem 2==1->打印偶数(I+1,N)
结束;
打印偶数(I,N)->
io:格式(“完成”)。
我真的想让最后一个案例自动退出,而不必在函数中打印任何内容。我试着删除它,但是当递归完成时,会抛出一个错误,因此会出现一个错误

我该怎么做?erlang中是否有类似于“pass”或“yield”的关键字?

我相信关键字是“
ok

只需返回一个atom即可

打印偶数(I,N)->完成


应该这样做。

您还可以在guard子句中结合测试。我还更喜欢done atom技巧——它在代码中显示,是function子句将停止“递归”

printfeen(I,N)当I
io:format(“~p是偶数~n,[I]),
打印偶数(I+1,N);
当我
打印偶数(I+1,N);
打印偶数(I,N)->
完成。

好的,首先定义函数:

printEven(I,N) when I >= N -> ok;
printEven(I,N)             -> 
   if
    I rem 2 == 0 -> io:format("~p~n",[I]), printEven(I+1,N);
    I rem 2 == 1 -> printEven(I+1,N)
  end.
ok = printEven(3,9),
Erlang是一种函数式编程语言,并且(根据定义)函数“有”一个值,因此您将获得“某些东西”。按照惯例,完成一个函数后,你得到的副作用是原子“ok”,这是这里最好使用的

如果需要,可以“静默地放弃”返回值。当您通过模式匹配到“不在乎”变量(下划线)来调用函数时,您可以这样做:

或者在没有模式匹配的情况下调用函数:

printEven(3,9),
但是,在调用函数时,最好始终通过模式匹配检查返回值:

printEven(I,N) when I >= N -> ok;
printEven(I,N)             -> 
   if
    I rem 2 == 0 -> io:format("~p~n",[I]), printEven(I+1,N);
    I rem 2 == 1 -> printEven(I+1,N)
  end.
ok = printEven(3,9),
这是一个非常好的习惯,因为您将使用大量返回错误代码的库函数,您可以从它们的规范中看到:

@spec funky(X) -> [ok | {error, bad_op} | {error, wig_out}]
如果funky有副作用,您希望通过模式匹配调用它,知道它现在失败了,所以它会在这里崩溃,如果funky失败:

ok = funky(99),
如果您将其与
匹配或忽略返回值,那么当您的魔咒期望funky完成他的任务时,它将崩溃268行,然后它将更难找到

这就是快乐路径编程,它是Erlang中完成的事情。“让它崩溃”是格言。如果你是新来的二郎,你会发现这非常令人不安-像裸体行走。别担心,拥抱它,这是件好事。这会导致很多代码“没有被编写”

(您还应该养成将结束递归的子句作为top子句的习惯,如图所示-当您使用多子句函数时,读取代码sooo会容易得多。)

为链中的每个函数调用填充返回值,得到:

printEven(1, 3) =>  ok
                    ^ 
                    |
              printEven(2, 3) => ok
                                 ^ 
                                 |
                         printEven(3, 3) => ok
                                            ^
                                            |
                                      printEven(4, 3) => ok 
这可以做到:

printEven(I,N) -> ok.

我不想让原子打印,只想打印文本中的数字。原子不会打印。它将停止循环。我应该澄清一下,您应该注意printEven的返回值从未使用过,因此您可以让它返回任何不包括递归调用的内容。仍然在shell中为我输出
done
。shell显示您调用的所有函数的返回值。是否有方法以静默方式退出?没有原子?否-所有函数都返回一个值。你没有测试函数的值,所以我不确定它为什么对你重要?嗯,这段代码无法编译-第一个子句必须以分号结束,而不是以句号结束。你在壳里运行吗?如果您是,它将始终打印它返回的内容,并始终返回一些内容。如果您没有在shell中运行它,那么只需删除io:format…实际上,这段代码不够漂亮,第二个子句应该写成:print偶数(I,N)->(如果I rem 2==0->io:format(“~p~N”,[I]);I rem 2==1->ok%不打印结束,打印偶数(I+1,N);请记住,if子句返回一个值-在本例中,您可能无法匹配它,但我坚持匹配是为了提醒您:)避免编写两次递归函数调用,不仅可以使事情变得更漂亮,通过避免用case语句编写两次
I rem 2
,您可以使事情变得更漂亮。看看我的答案。
printEven(1, 3) =>  ok
                    ^ 
                    |
              printEven(2, 3) => ok
                                 ^ 
                                 |
                         printEven(3, 3) => ok
                                            ^
                                            |
                                      printEven(4, 3) => ok 
printEven(I,N) -> ok.