erlang"非法守卫表达"在卫兵中使用功能

时间:2015-12-15 17:07:22

标签: erlang

我有以下代码。我正在检查3个条件。您可以查看第一个条件,我将xml:get_tag_attr_s(...)的输出存储在变量中,然后在if块中使用该变量。我的问题是我得到错误illegal guard expression,如果我尝试在一行中执行上述过程,就像我在其他两个条件中那样。

另外,我从默认条件获得variable '_' is unbound。它应该是一回事。

有人可以解释一下这个问题吗?

validate_xmpp(Packet) ->
      Type = xml:get_tag_attr_s(list_to_binary("type"), Packet),
      if
          (Type /= <<"chat">> ->
              {error, "Message type is not chat"};
          xml:get_path_s(Packet, [{elem, list_to_binary("body")}, cdata]) /= <<"">> ->
              {error, "No or empty body"};
          exml_query:path(Packet, [{element,<<"received">>},{attr,<<"xmlns">>}]) == <<"urn:xmpp:receipts">> ->
              {error, "delivery-receipts should be ignored"};
          _->
              {ok, xml:get_tag_attr_s(list_to_binary("from"), Packet)}
      end.

2 个答案:

答案 0 :(得分:9)

Erlang只允许这些守卫:

  • 原子真实
  • 其他常量(术语和约束变量),均视为假
  • 调用表类型测试BIF中指定的BIF
  • 术语比较
  • 算术表达式
  • 布尔表达式
  • 短路表达式(andalso / orelse)

有关详细信息,请查看http://www.erlang.org/doc/reference_manual/expressions.html#id83606

而不是this使用_。您不能仅在true语句中使用_中的if,还可以查看docs

答案 1 :(得分:1)

isPrime(A,B) when B>math:sqrt(A) -> true;

这将导致非法的防护错误。

初读时,警卫似乎包含“条款比较”:

>

和“算术表达式”:

math:sqrt(A)

富特莫尔,如果您玩弄代码,就会发现后卫:

B > A+2 

是合法的。那么“算术表达式” math:sqrt(A)A+2有什么区别?

Erlang docs将“算术表达式”定义为:`

+   
- 
*
/
div
rem
bnot
band
bor
bxor
bsl
bsr

值得注意的是,math:sqrt()不在“算术表达式”列表中。因此,math:sqrt(A)是一个“函数调用”,而不是“算术表达式”,并且您只能在防护中调用一定数量的函数,即在here中列出的“类型测试BIF”,例如:

is_integer/1
is_float/1
is_binary/1
is_list/1
is_map/1
is_function/1
etc.