【问题标题】:C++ Most efficient way for storing, loading and looking up a lexiconC++ 存储、加载和查找词典的最有效方式
【发布时间】:2013-05-22 00:54:15
【问题描述】:

我有一本包含单词及其音标的字典。 单词都是小写的,所以不涉及区分大小写的搜索。

词典非常庞大,我需要在我的应用程序启动时快速加载它。 我宁愿阅读它而不必单独阅读每个条目。

我猜我存储和加载它的方式也会影响我将词典保存在内存中的方式

感谢您的任何想法。

【问题讨论】:

  • “真正巨大”有多大?您打算将整个词典加载到应用程序的内存中,还是从文件或数据库中读取?此外,该结构需要有效执行哪些类型的操作?主要是查找,还是枚举?
  • 真正巨大的意义 200.000 字。我想把它加载到内存中。我只需要查字,不写也不显示。
  • 你需要用“typos”和wild-chars搜索吗?
  • @MartinPerry 不,只是 1:1 查找。

标签: c++ dictionary lexicon


【解决方案1】:

您可能希望将其存储为 Trie

这是一种存储字典的有效方式。查看以下答案以获取更多信息

http://en.wikipedia.org/wiki/Trie

https://stackoverflow.com/questions/296618/what-is-the-most-common-use-of-the-trie-data-structure

Persisting a trie to a file - C

【讨论】:

  • 请注意,除非特别注意,否则 trie 将有相当大的内存需求。
  • 虽然操作得当,但由于前缀压缩,trie 可能是存储字典的最有效方式。
【解决方案2】:

想到几个选项:

  1. 您可以使用sqlite,它使用mmap 将文件映射到内存,以存储词典,以便仅读取访问的内容。这可能是合理的快速和可靠的,也是最容易实现的。
  2. 您可以自己mmap该文件
  3. 使用seek 操作在文件中移动文件指针而不读取整个文件。这只有在词典以某种方式构建时才有帮助,这样您就可以在不阅读所有内容的情况下找到正确的位置,即它必须是一个允许比 O(n) 搜索更好的数据结构(Trie 通常是一个不错的选择,因为Salgar 建议)。

【讨论】:

  • 假设我对文件进行内存映射,并且我知道单词从哪个位置开始(例如:“a”单词从 pos 1 开始,“b”单词从 pos 93229 开始),如何我构建我的文件?我必须使用固定长度还是映射文件是什么意思?
  • 我的应用程序是纯 C++ 代码,没有任何第三方库,虽然我喜欢 SQLite,但在这种情况下我会选择不使用它。
  • 结合两个答案,然后mmap一个trie。
  • 如果您确切地知道在哪里看:太好了,这应该在结构方面有效(或者您可以使用 trie)。 mmap 将文件的一部分映射到内存,因此您可以像访问数组一样访问它。查看手册页。它也有一个很好的例子来说明如何做到这一点。请注意,这种低级方法不适合胆小的人,因为您必须在其他事情中对偏移量进行页面对齐。
  • @smocking 我不确定对字典进行映射是如何工作的。即使我可以快速访问字节,我将如何搜索条目?我想我必须遍历整个地图。在我看来,这没有任何意义。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-05-26
  • 2015-04-30
  • 1970-01-01
相关资源
最近更新 更多