【问题标题】:StarDict support for JavaScript and a Firefox OS AppStarDict 对 JavaScript 和 Firefox OS 应用程序的支持
【发布时间】:2013-08-14 00:11:24
【问题描述】:

我本着 GoldenDict 的精神(www.goldendict.org,更多信息请参见 Google Play Store)编写了一个词典应用程序:http://tuxor1337.github.io/firedicthttps://marketplace.firefox.com/app/firedict

由于 ffos 应用程序基于 HTML、CSS 和 JavaScript(WebAPI 等),我必须从头开始编写所有内容。一开始,我用 JavaScript 写了一个用于同步和异步访问 StarDict 字典的基本库:https://github.com/tuxor1337/stardict.js

虽然该应用程序现在可以称为稳定,但整体性能仍然有点迟钝。对于某些词典,我有一个包含近 1,000,000 个词条的单词列表!那是巨大的。索引需要很长时间(每个字典最多几分钟)和查找。目前,单词存储在 IndexedDB 对象存储中。还有其他选择吗?使用当前的解决方案(使用二进制搜索访问和插入的单词),整体体验非常缓慢。 也许它会变得更快,如果 IndexedDB 有一些语言环境排序支持... 实际上,我什至没有将术语本身存储在数据库中,而只是将它们的偏移量存储在 *.syn/* .idx 文件。我希望这样做可以节省一些内存。但当然,我无法在此配置中使用任何 IDB 排序功能...

也许在内存中进行排序不是最好的主意,因为现在由于某些设备(例如 ZTE Open)上的 OOM 导致应用程序被内核杀死。超过 500,000 个条目的字典肯定会超过 100 MB 的内存。 (每个条目只有 200 字节,如果您假设关键字字符串是 UTF-8,那么您将立即超过 100 MB...)

请随意直接为 GitHub 上的项目做出贡献。否则,我很乐意听取您对上述问题的建议。

【问题讨论】:

  • 虽然这不能解决您的问题,但需要长期努力将基于区域设置的排序添加到 IDB。我们需要它用于其他 Firefox OS 应用程序。见这里:bugzilla.mozilla.org/show_bug.cgi?id=871846
  • 见上文,我添加到问题中:我不能使用任何 IndexedDB 的排序功能,因为我不想将术语本身存储在数据库中,而只是(整数)引用存储在 StarDict 格式的 idx/syn 文件中的术语。
  • 我已经在下面更新了我的答案,希望你看看。

标签: javascript data-structures firefox-os html5-apps


【解决方案1】:

我正在开发与您的 stardict 项目类似的 MDict 解析器 (https://github.com/fengdh/mdict-js) 的纯 Javascript 实现。 MDict是另一种流行的字典格式,格式丰富(嵌入图像/音频/css等),在window/linux/ios/android/windows手机上得到广泛支持。我有一些想法要分享,希望您将来可以将其应用于改进stardict.js。

MDict字典文件(mdx/mdd)将关键字和记录分成(可选压缩)块,每个包含大约2000个条目,并提供关键字块索引表和记录块索引表,以帮助快速查找。由于其紧凑的数据结构,我可以直接在字典文件上实现我的 MDict 解析器扫描,具有较小的预加载索引表,但 不需要 IndexDB

  • 每个关键字块索引如下所示:

    {num_entries: .., 
     first_word: .., 
     last_word: .., 
     comp_size: ..,    // size in compression 
     decomp_size: ..,  // size after decompression
     offset: ..,       // offset in mdx file
     index: ..
    }
    
  • 在keyblock中,每个entry是一对[keyword,offset]

  • 每个记录块索引如下:

    {comp_size: ..,    // size in compression 
     decomp_size: ..,  // size after decompression
    }
    
  • 给定一个词,使用二分法查找可能包含它的关键字块。

  • 切片关键字块并加载其中的所有关键字,过滤掉匹配的关键字并获取其记录偏移量。
  • 使用二分法查找包含单词记录的记录块。
  • 切片记录块并直接检索其记录(文本中的定义或 ArrayBuffer 中的资源)。

由于每个块仅包含大约 2000 个条目,因此在 100 毫秒内从 100K~1M 的字典条目中查找单词已经足够快,对于人类交互来说是相当不错的价值。 mdict-js 只解析文件头,速度超快,内存占用低。

同样,即使使用通配符,也可以检索给定短语的相邻单词列表。

请在此处查看我的在线演示:http://fengdh.github.io/mdict-js/ (你必须选择一个本地的MDict字典:一个mdx + 可选的mdd文件)

【讨论】:

  • 感谢您的回答!您所描述的与我所做的非常相似(直接在文件中进行二进制搜索)。事实上,mdict 格式与使用 dictzip 压缩时的 stardict 格式非常相似。一旦您的项目有某种 API 文档,也许我会向 FireDict 添加 mdict 支持:)
  • 我也受到了您的项目的启发。欢迎您使用/修改我的代码。请查看我的代码中的文档,或联系我以获取更多问题。我希望在像您这样受人尊敬的人的帮助下改进我的代码。
猜你喜欢
  • 1970-01-01
  • 2012-12-02
  • 2012-02-11
  • 2013-02-14
  • 2013-05-23
  • 1970-01-01
  • 1970-01-01
  • 2014-03-25
  • 2013-07-02
相关资源
最近更新 更多