本文最后更新于:June 30, 2023 pm

ETS 表可以用来高效存储海量的erlang数据,ETS提供大型的键-值查询表,

1.四种不同的类型

  • 集合(set)

    相同的key-value元组只能出现一次。

  • 包(bag)

    每种key-value元组组合只能出现一次,但是同一个key可以出现多次。

  • 重复包(duplicate bag)

    允许重复的元组。

  • 有序集合(ordered set)

    相同的key-value元组只能出现一次,但是可以按key的顺序访问各个元组。

访问有序集合(ordered set)类型中的元素需要消耗表长度的对数级别的时间(oLog n),访问其余类型的元素只需要消耗常量级别的时间。

2.表权限

  • public

    允许任何进程访问(读写)。

  • private

    只有拥有该表的进程才能访问。

  • protected

    任何进程都可以读,只有拥有该表的进程才能写入。

3.其它参数

  • {keypos, N}

    创建表的时候可以通过 {keypos, N} 指定键取自那个位置,对存储记录record非常的有用。

  • named_table

    如果存在此选项,则以表的名称注册该表,然后在后续的操作使用该表名称而不是表的标识符。要获取指定标的标识符,可以使用 whereis/1。

  • {write_concurrency, boolean()}

    默认为false。这种情况下,对表的写入修改的操作获得独占访问,阻塞对同一表的任何并发访问。如果设置为true,则表将优化为并发写访问。

  • {read_concurrency, boolean()}

    默认为false。如果设置为true,则该表将优化为并发读访问。

  • compressed

    压缩,如果存在此选项,那么将以更紧凑的格式存储表数据,以消耗更少的内存。但是,这会使表操作变慢。特别是需要查找整个对象(如match,select)这种操作,速度会慢很多,关键元素不会被压缩。

4. 匹配

ETS的查询方式遵循模式匹配,下面用例子说明:

表结构 :

#trap_client_info{id , client_id  ,auth ,transport ,socket ,ip }

匹配:

 ets:match(trap_connection_table,{'_',{trap_client_info,'$1','$2', '$3', '$4','$5','$6'}}).
 结果:
[[1,<<"4d45d94142276ad38364049c56d8ed43">>,
  {127,0,0,1},
  true,esockd_transport,#Port<0.48>]]

 ets:match(trap_connection_table,{'_',{trap_client_info,'$1','$2', '$3', '$4','$5','_'}}).  
结果:
[[1,<<"4d45d94142276ad38364049c56d8ed43">>,
  {127,0,0,1},
  true,esockd_transport]]

通过上面的两个匹配语句,我们发现规律:

  • 如果要匹配指定的字段,我们可以用’$N’原子来实现
  • 如果过滤字段,我们用’_’原子来实现。
    想一下SQL的写法:
    select * from trap_connection_table;

对应:

ets:match(trap_connection_table,{'_',{trap_client_info,'$1','$2', '$3', '$4','$5','$6'}}).
select id,client_id from trap_connection_table;

对应:

ets:match(trap_connection_table,{'_',{trap_client_info,'$1','$2', '_', '_','_','_'}}).

注意:$N会根据N进行排序,数字越大顺序越后。’_’表示我们忽略不要的字段。


本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!

运行时错误 Previous
Linux下安装Erlang和SSL Next