使用潜在的多项式Big O运行时间优化代码

时间:2019-04-23 16:11:47

标签: python recursion big-o

在我的一次采访中,有人问我一个问题,以确定给定的字符串是否是有效的英语短语。所讨论的字符串是字母数字字符的集合,没有分隔符,包括空格。假设某个地方有一个“字典”,其中包含所有有效单词,可以用作确定单词是否有效的参考。可以使用任何适当的机制/数据结构来实现此“字典”。

我的解决方案是使用Python完成的,并且涉及到递归。这是我的建议:

def isphrase(string, words):
"""
Determine if a given string (containing no spaces or delimiters) is a 
valid English phrase
:param string: String to be checked
:param words: Collection of English words as an iterable or in a file
:return:  True, if it is a phrase
         False, otherwise
"""

if len(string) == 0:
    return True

if string in words:
    return True

for i in range(len(string)):
    if string[:i+1] in words and isphrase(string[i+1:], words):
        return True

return False


if __name__ == '__main__':
    words = {"i", "am", "here", "there", "you", "were"}
    print(isphrase("thereyou", words))

该解决方案被认为是可行的解决方案,但是在计算时间复杂度的同时,在更糟的情况下这会变成O(n!)。有没有办法使它更接近O(nlogn)或类似的东西?我是否应该采用分而治之的哲学而不是这种方法?

P.S:我使用了一个集合来保存单词集合。也请随时提供您的建议/意见。

1 个答案:

答案 0 :(得分:0)

这是一个动态编程解决方案:

def isphrase(s, word_dict):
    size = len(s)

    if size == 0:
        return False

    dp = [False]*(size+1)
    dp[0] = True
    for i in range(size):
        if dp[i]:
            for j in range(i, size):
                if s[i:j+1] in word_dict:
                    dp[j+1] = True
    return dp[j+1]

if __name__ == '__main__':
    words = {"i", "am", "here", "there", "you", "were"}
    print(isphrase("thereyou", words))

您可以将子词保留在列表中,这样就不会经常重新计算它们。更快的解决方案是使用自上而下的动态编程方法(留给读者练习),或者可以使用Trie。