如何匹配 ets:match 与 Erlang 中的记录?
我听说在代码中通过元组指定记录是一种不好的做法:我应该始终使用记录字段 (#record_name{record_field = some}
) 而不是普通元组 {record_name, value1, value2,某事}
。
但如何将记录与 ETS 表进行匹配呢?如果我有一个包含记录的表,我只能匹配以下内容:
ets:match(Table, {$1,$2,$3,something}
显然,一旦我向记录定义添加一些新字段,此模式匹配将停止工作。
相反,我想使用这样的东西:
ets:match(Table, #record_name{record_field=something})
不幸的是,它返回一个空列表。
I have heard that specifying records through tuples in the code is a bad practice: I should always use record fields (#record_name{record_field = something}
) instead of plain tuples {record_name, value1, value2, something}
.
But how do I match the record against an ETS table? If I have a table with records, I can only match with the following:
ets:match(Table, {$1,$2,$3,something}
It is obvious that once I add some new fields to the record definition this pattern match will stop working.
Instead, I would like to use something like this:
ets:match(Table, #record_name{record_field=something})
Unfortunately, it returns an empty list.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
问题的原因是当您执行
#record_name{record_field=something}
时未指定的字段被设置为什么。这是创建记录的语法,在这里您将创建一个记录/元组,ETS 将其解释为模式。当您创建记录时,所有未指定的字段都将获得其默认值,要么是在记录定义中定义的值,要么是默认值undefined
。因此,如果您想为字段指定特定值,则必须在记录中显式执行此操作,例如
#record_name{f1='$1',f2='$2',record_field=something}
。通常,在使用记录和 ets 时,您希望将所有未指定的字段设置为'_'
,即 ets 匹配的“无关变量”。为此有一种特殊的语法,使用特殊的、否则非法的字段名称_
。例如#record_name{record_field=something,_='_'}
。请注意,在您的示例中,您已将元组中的记录名称元素设置为“$1”。表示记录的元组始终将记录名称作为第一个元素。这意味着当您创建 ets 表时,您应该将
{keypos,Pos}
的关键位置设置为默认1
以外的其他位置,否则不会有任何索引更糟糕的是,如果您有一个“set”或“ordered_set”类型的表,您将只能在表中获得 1 个元素。要获取记录字段的索引,您可以在示例中使用语法#Record.Field
,例如#record_name.record_field
。The cause of your problem is what the unspecified fields are set to when you do a
#record_name{record_field=something}
. This is the syntax for creating a record, here you are creating a record/tuple which ETS will interpret as a pattern. When you create a record then all the unspecified fields will get their default values, either ones defined in the record definition or the default default valueundefined
.So if you want to give fields specific values then you must explicitly do this in the record, for example
#record_name{f1='$1',f2='$2',record_field=something}
. Often when using records and ets you want to set all the unspecified fields to'_'
, the "don't care variable" for ets matching. There is a special syntax for this using the special, and otherwise illegal, field name_
. For example#record_name{record_field=something,_='_'}
.Note that in your example you have set the the record name element in the tuple to '$1'. The tuple representing a record always has the record name as the first element. This means that when you create the ets table you should set the key position with
{keypos,Pos}
to something other than the default1
otherwise there won't be any indexing and worse if you have a table of type 'set' or 'ordered_set' you will only get 1 element in the table. To get the index of a record field you can use the syntax#Record.Field
, in your example#record_name.record_field
.尝试使用
请参阅此进行解释。
Try using
See this for explanation.
您要查找的格式是 #record_name{record_field=something, _ = '_'}
http://www.erlang.org/doc/man/ets.html#match-2
http://www.erlang.org/doc/programming_examples/records.html(参见1.3创建记录)
Format you are looking for is #record_name{record_field=something, _ = '_'}
http://www.erlang.org/doc/man/ets.html#match-2
http://www.erlang.org/doc/programming_examples/records.html (see 1.3 Creating a record)