使用ets表进行gen_server状态

时间:2010-11-24 19:31:12

标签: erlang gen-server

我正在编写一个gen_server,我希望将ets表作为一个状态,然后在其他地方创建了ets表。我该如何将它添加到gen_server的状态?

我想使用ets表而不是为它创建一个新的字典,因为我想节省内存。

另外,如何迭代ets表?我想迭代或读取表中的每个值并检查值,然后我想根据值执行两个选项之一。

将ets表转换为列表并遍历列表会更容易吗?

由于

1 个答案:

答案 0 :(得分:4)

一些建议:

  • 阅读ETS手册页:erl -man ets
  • ETS表由其名称(在named_table选项的情况下)或其表ID标识。将该信息传递给gen_server并将其保持在以下状态:

    -record(state, { ..., tbl = none }).
    
    
    init([TableID]) ->
        ...,
        {ok, #state { tbl = TableID }}.
    

ETS可能无法节省那么多内存。有一个新标志出现在后来的Erlang / OTP版本中,其中ETS表可以是compressed,因此它们的内容在存储之前被压缩并且在读取时被解压缩(这有计算开销)。

要遍历ETS表,您有几个选项。 ets:first/1 ets:next/2就是这样一个界面。 ets:foldl/3 ets:foldr/3另一个。 ets:match/3为你提供了一个继续(光标)。 ets:select比匹配更为通用。

将它变成列表会更容易吗?这取决于。 ETS表的强大之处在于它们有一个选项{keypos, N},用于定义存储元素的键。 ets:lookup(?TAB, Key)非常快,因此您可以快速查找密钥。列表不是这样。但另一方面,如果你总是遍历所有列表,它可能是一个更简单的解决方案(只要你没有在进程之间传递大的列表)。

或许应该避免将整个表转换为列表并遍历它。您将在内存中生成列表,然后遍历它,这是昂贵的。最好一次遍历它,以便实时内存量很少。