首先声明我正在学习 erlang。这里根本不是专家。在使用 ETS 制作一些示例时,我遇到了一些我不理解的东西(即使在搜索之后)。
我有一个创建公共 ETS 的过程
TableID = ets:new(tablename, [public])}
然后我将 TableID 传递给其他进程。当我从外壳运行模块时,一切正常。当我使用 erl -noshell -s ... 甚至没有 -noshell 选项运行完全相同的模块时,它会失败。我不断收到错误:badarg,好像表格不存在一样。ID 正确通过,但表实际上表现得像私有的!
从 shell 交互运行模块与不运行模块有区别吗?
谢谢
我正在添加我用来尝试调试问题的代码示例。由于它是一个更大的软件的一部分(而且它基本上是为了找到问题而被剥离的),它可能很难理解。
-record(loop_state, {
commands
}).
start() ->
LoopState = #loop_state{commands = ets:new(commands, [public])},
tcpserver_otp_backend:start(?MODULE, 7000, {?MODULE, loop}, LoopState).
loop(Socket, LoopState = #loop_state{commands = Commands}) ->
case gen_tcp:recv(Socket, 0) of
{ok, Data} ->
% the call below fails, no error generated, AND only in non interactive shell
A = newCommand(Commands, Data),
gen_tcp:send(Socket, A),
loop(Socket, LoopState);
{error, closed} ->
ok
end.
newCommand(CommandTableId, Command) ->
case ets:lookup(CommandTableId,Command) of
[] ->
_A = ets:insert(CommandTableId, {Command, 1}),
<<1, "new", "1">>; % used for testing
_ ->
<<1, "old", "1">> % used for testing
end.
当我删除“有问题的命令”ets:lookup 时,一切都再次作为交互式 shell 工作。