erlang-如何将元组内容与qlc和mnesia匹配?

erlang-如何将元组内容与qlc和mnesia匹配?,erlang,mnesia,Erlang,Mnesia,我有这张唱片的记忆表 -record(peer, { peer_key, %% key is the tuple {FileId, PeerId} last_seen, last_event, uploaded = 0, downloaded = 0, left = 0, ip_port, key }). Peer_key是一个元组{FileId,ClientId},现在我需要从所有具有特定FileId的Peer中提取ip_p

我有这张唱片的记忆表

-record(peer, {
    peer_key,   %% key is the tuple {FileId, PeerId}
    last_seen,
    last_event,
    uploaded = 0,
    downloaded = 0,
    left = 0,
    ip_port,
    key
}).
Peer_key是一个元组{FileId,ClientId},现在我需要从所有具有特定FileId的Peer中提取ip_port字段

我提出了一个可行的解决方案,但我不确定这是否是一个好方法:

qlc:q([IpPort || #peer{peer_key={FileId,_}, ip_port=IpPort} <- mnesia:table(peer), FileId=:=RequiredFileId])

qlc:q([IpPort | |#peer{peer_key={FileId,},ip_port=IpPort}您的查询时间将随着表大小线性增长,因为它需要扫描所有行。因此,请使用实际的表数据对其进行基准测试,以查看它是否确实可行

如果您需要加快速度,您应该专注于能够快速找到携带文件id的所有对等方。这可以通过将[fileid,peerid]作为属性的bag类型的表来完成。给定文件id,您将获得所有对等方id。这样,您就可以构造对等表键进行查找

当然,您还需要在更改对等表的每个事务中维护该包类型表


另一种选择是重复fileid并在该列上添加一个mnesia索引。我只是没有将其添加到mnesia自己的二级索引中。

使用带有元组主键(如{fileid,PeerId})的有序集合表类型,然后部分绑定元组前缀(如{RequiredFileId,}将非常有效,因为将只检查具有该前缀的键的范围,而不是完整的表扫描。您可以使用qlc:info/1检查查询计划,并确保正在进行的任何选择都绑定了键前缀