【问题标题】:Check if a string containing 2 words is in a dictionary检查包含 2 个单词的字符串是否在字典中
【发布时间】:2011-05-26 19:45:20
【问题描述】:

我有一个字典单词数组和一个像“twowords”这样的随机字符串

检查整个字符串是否由字典单词组成的最快方法是什么?所以“twojwords”会返回false,“twowords”会返回true

我之前使用过二分查找,但它无法处理两个字符串

(我正在使用目标 c)

【问题讨论】:

  • 为了优化,问题总是两个成员的话,还是你想把它扩展到更多的成员(比如“mytwocents”或“iwanthamburger”)?
  • 超过两个成员但字符串总是7个字母长,所以“ilikeyo”也应该返回true
  • @GeeGoldz,即使“哟”不是一个词?
  • @rdineiu 它必须是一个词,我只是举个例子,因为你很长
  • 7 个字母是重要的输入。所以候选人总是 7 个字母长,而你的字典条目是 1 到 7 个字母?这是否紧急,因为如果不是,我将实施我的一些想法并进行一些速度测量。

标签: algorithm optimization


【解决方案1】:

测试每个子字符串的另一种方法是从您的字典中构建一个 trie 并遍历它,一次一个字母,例如 BFS。我们不仅要跟踪当前节点,还要跟踪节点以及我们看到了多少单词。在每个节点,如果可用,则将下一个字母排入队列,如果当前节点是终端节点,则将开始节点(加上 1 个单词)排入队列。如果我们到达字符串的末尾并且在开始节点处有 2 个单词,那么有一个解决方案。

这巧妙地概括为两个以上的词。我不确定在最坏的情况下它是否比字符串吐痰更快,但它可能会更快,因为a)没有单词生成b)我们知道第n个字符串在测试第n + 1个之前在字典中

【讨论】:

  • 听起来不错但是对我来说太复杂了,substring方法很简单
  • 耸耸肩 - 你不是在抱怨另一种解决方案太明显了吗?
  • 我没有看到自己在任何地方抱怨
  • 对不起,我误解了你的一个 cmets
  • 您绝对应该研究 BFS(广度优先搜索)。如果您还不知道,它是几乎所有其他问题中出现的最重要的算法之一。理解它,会让你更好地解决大多数其他问题。
【解决方案2】:

这里是一个幼稚的方法,但我不知道是否有更快的方法。

for i1 from 0 to 6 do
  substring1 = string[0..i1];
  if (inDictionary(substring1)) {
    for i2 from i1+1 to 6 do
      substring2 = string[i1+1..i2];
      if (inDictionary(substring2)) {
        for i3 from i2+1 to 6 do 
... (up to i6)

为此,您需要能够形成字符串的字母 a 到 b 的子字符串。例如。如果string = "thisisastring" 那么string[4..7] = "isas"。您还需要一个布尔函数 inDictionary,它应该对字典中的子字符串进行二进制搜索。

此方法可行,但根据字典的大小,可能需要一些时间。我认为英语目前在 200000 字左右,在这种情况下,任何合理的编程语言都应该有合理的性能。

【讨论】:

  • 这是个好主意,但 string[0..i1] 在该语言中是什么意思?
  • string[a..b] 表示从第a个字母开始,到第b个字母
  • 啊,这很明显,谢谢。我再等一会儿再选择你的答案
  • 看看你有没有更聪明的方法。我自己看不出有什么办法可以避免这种情况,但我并没有谎称自己是 SO 上最聪明的人。
【解决方案3】:

首先,它将为您的字典使用某种哈希表数据结构,为您提供 ~O(1) 的单字查找。这比二分查找好很多,尤其是当您的字典大小为 200,000 时

对于两个单词,将您的字符串分成两半,例如 t-wowords、two-owords、two-words、twoword-ords 等,并为每一半进行查找。

如果您想允许任意数量的部分,您应该尝试递归方法。在伪代码中:

bool checkWord(string word)
{
    if(length(word)==1)
        return isWordInDict(word);
    for each pair w1, w2 of word halfs
    {
        if(isWordInDict(w1) && checkWord(w2))
            return true;
    }
    return false;
}  

【讨论】:

  • 这是最好的解决方案。
猜你喜欢
  • 2014-01-25
  • 2016-11-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-05-20
  • 2013-03-04
  • 2013-12-23
  • 1970-01-01
相关资源
最近更新 更多