【问题标题】:How to find the position of words in a string? [duplicate]如何查找字符串中单词的位置? [复制]
【发布时间】:2016-12-06 03:50:28
【问题描述】:

问题来了:

使用以下输入和输出编写一个名为 wordPositions() 的函数。 输入:s,一个由大小写字母和空格组成的字符串。 返回:一个字典,其中 s 中的每个不同单词都是一个键,对应的值是该单词在 s 中出现的位置的列表。无论大小写如何,单词都将被视为相同。也就是说,“是”和“是”是同一个词。 以下是正确输出的示例。

s = 'One fish two fish red fish blue fish' 

wp = wordPositions(s) 

print(wp) 

{'two': [2], 'one': [0], 'red': [4], 'fish': [1, 3, 5, 7], 'blue': [6]}

现在这是我的代码:

def wordPositions(s):
aDict = {}
words = s.split(' ')
for item in words:
    position = words.index(item)
    aDict[item] = position
print(aDict)
print(wordPositions('One fish two fish red fish blue fish'))

问题是我的输出:

{'two': 2, 'blue': 6, 'red': 4, 'fish': 1, 'One': 0}

如何让它看起来像教授的?另外,请注意在我的输出中,单词“fish”仅显示它的一个位置,尽管它在字符串中重复出现。如何让 Python 显示“鱼”的多个位置?

【问题讨论】:

  • 您的字典需要保存列表。对于这个,您可能需要查看defaultdict 以允许您的字典条目默认为列表。接下来是使用enumerate 进行迭代。如果您使用索引(没有start 参数),它将继续找到相同的索引,更不用说它会给您的代码On^2 时间复杂度。考虑for i, word in enumerate('One fish two fish red fish blue fish'.split()): print(i, word)

标签: python string python-3.4


【解决方案1】:

每次您找到一个单词的位置并存储它时,您都会覆盖该键的值(如果之前找到了该单词),而不是为其添加另一个值。

不要将位置值直接分配给字典项。相反,您需要为每个字典项分配一个数组。然后,每次找到单词的位置时,您都可以将新值推送到数组中。

首先,您需要检查该键是否已存在于字典中。如果没有,请先为该键分配一个空数组。然后(无论该键之前是否存在)将新值推送到数组(即作为该键的值的数组)。

编辑:另请注意,position = words.index(item) 获取项目在 word 中第一次出现的位置。所以你需要确保单词的位置不重复(提示:使用for循环来做到这一点)。

(向发送上述编辑的@Cham K. 道歉 - 我不确定如何自动接受它。)

编辑 2(根据 @TigerhawkT3 评论):在您的 for 循环中使用 enumerate。在这种情况下使用起来更简单。 (谷歌python枚举)。

注意:我故意不在此处发布代码。只是(希望有帮助)说明。看起来你应该自己去想办法。 :-)

【讨论】:

  • 我还建议推荐enumerate
  • @TigerhawkT3 是的。如果字符串中的每个单词总是用空格分隔,这就是我要采取的方法。
  • 我认为您是在开玩笑,并且您并不是真的要求其他人为您做作业。另见meta.stackexchange.com/questions/18242/…meta.stackoverflow.com/questions/334822/…
  • @Jorgan 如果这件事在午夜到期,你为什么不早点做?
  • @Jorgan 对您的帮助不太客气,期待别人做你的工作不是 SO 的目的。
【解决方案2】:

试试这个:

def wordPositions(s):
    aDict = {}
    words = s.split(' ')
    for item in words:
        aDict[item]=""
    for i in range(0,len(words)):
        if aDict[words[i]]=="":
            aDict[words[i]]=str(i)
        else:
            aDict[words[i]] = aDict[words[i]]+","+str(i)
    print(aDict)
wordPositions('One fish two fish red fish blue fish')

【讨论】:

    【解决方案3】:

    Pythonic 方式可能是以下字典理解:

    def wordPositions(s):
        splitted = s.split()
        return {w: [i for i in range(len(splitted)) if splitted[i] == w]
                    for w in set(splitted)}
    

    正如 BallpointBen 在 cmets 中指出的那样,从复杂性的角度来看,这个解决方案并不是一个好的解决方案,因为它是一个 O(n^2) (一个循环嵌入在集合上的循环内的列表上)。

    虽然它看起来不错,因为它是一个 Pythonic 解决方案,它同时使用了字典和列表理解。

    要吸取的教训是,Pythonicity 很好,但不是每次都好。

    【讨论】:

    • 请注意,这是 O(n^2),而最优解是 O(n)。
    • @BallpointBen 我知道这一点 :) 我认为这在复杂性和可读性方面都很糟糕,但它仍然是一种 Pythonic 方式。实际上,我发布此答案是为了指出处理此类问题的理解方式。
    • 不错!我想知道教授是否可以这样做?
    • @SonofaBeach 你是说那个线程?
    • 字典理解中的列表理解。而这整个线程。 :-)
    【解决方案4】:

    您的教授要求您创建一个整数位置列表作为字典的值,但是您的方法仅将整数作为值。因此正确的方法是在循环中创建一个新列表并在找到新位置时继续追加。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-10-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多