Erlang spawn_link/3 的错误参数错误

Posted

技术标签:

【中文标题】Erlang spawn_link/3 的错误参数错误【英文标题】:Bad Argument Error with Erlang spawn_link/3 【发布时间】:2016-03-03 13:52:38 【问题描述】:

我正在尝试编写一个并行排序的 Qsort 函数,并且将此代码直接转换为 Elixir 是可行的,但由于某种原因,当我运行 pqsort:pqsort([5, 4, 3, 10, 1]). 时它失败并出现以下错误:

** exception error: bad argument
     in function  spawn_link/3
        called as spawn_link(pqsort,#Fun<pqsort.0.102886275>,[<0.33.0>,[3,2,1]])
     in call from pqsort:pqsort_worker/2 (pqsort.erl, line 6)

这是我的代码:

-module(pqsort).
-export([pqsort/1, pqsort_worker/2]).

pqsort_worker(Listener, []) -> Listener ! self(), [];
pqsort_worker(Listener, [H | T]) ->
    PID_1 = spawn_link(pqsort, fun pqsort_worker/2, [self(), [ X || X <- T, H >= X ]]),
    PID_2 = spawn_link(pqsort, fun pqsort_worker/2, [self(), [ Y || Y <- T, H < Y ]]),
    receive
        PID_1, List_1 ->
            receive
                PID_2, List_2 -> Listener ! self(), List_1 ++ [H] ++ List_2
            end;
        PID_2, List_2 ->
            receive
                PID_1, List_1 -> Listener ! self(), List_1 ++ [H] ++ List_2
            end
    end.

pqsort(List) -> element(2, pqsort_worker(self(), List)).

【问题讨论】:

你确实意识到与 qsort 相比这是一个巨大的悲观? 是的...这只是我在试验 Erlang 并行性。我真的不打算让这更快。我只是在胡闹。 标题变化让问题完全不同。检查 spawn_link/3 的 typespec:erlang.org/doc/man/erlang.html#spawn_link-3 第二个参数是原子,而不是乐趣。 Funs 具有 arity 并且已经构建——Erlang 允许您使用函数的标签 + args 列表(其长度决定 arity)在需要 Mod, Fun, Args 类型值的任何地方动态调用函数。 【参考方案1】:

如果你去documentation,你会注意到第二个参数不是一个函数而是一个原子

只是改变

PID_1 = spawn_link(pqsort, fun pqsort_worker/2, [self(), [ X || X <- T, H >= X ]]),
PID_2 = spawn_link(pqsort, fun pqsort_worker/2, [self(), [ Y || Y <- T, H < Y ]]),

PID_1 = spawn_link(pqsort, pqsort_worker, [self(), [ X || X <- T, H >= X ]]),              |(emacs@Mac-mini-de-Rodrigo)1> c("/Users/rorra/erlang/pqsort", [outdir, "/Users/rorra/erlang/"\
PID_2 = spawn_link(pqsort, pqsort_worker, [self(), [ Y || Y <- T, H < Y ]]),  

【讨论】:

哦!谢谢!你能解释一下区别吗?我认为所有一流的函数都必须使用 fun 关键字来限定。 @ChristopherDumas 当您查看文档时:erlang.org/doc/man/erlang.html#spawn-3 您会注意到第二个参数不是函数而是原子。如果我的回答解决了这个问题,请随时接受它作为问题的正确答案,谢谢:) 我真的很喜欢你的回答。也许您可以将您的解释添加到未来人们的实际答案中?

以上是关于Erlang spawn_link/3 的错误参数错误的主要内容,如果未能解决你的问题,请参考以下文章

erlang ets 选择错误的参数

在 Erlang 中通过 tcp 套接字发送元组

Erlang 错误处理

无法在 Erlang 中运行 fsm

Erlang/OTP ./configure 失败 打开 Solaris

Erlang:打印第一个参数和第二个参数之间的素数列表