【问题标题】:Create tuples consisting of pairs of words创建由单词对组成的元组
【发布时间】:2016-01-16 07:01:26
【问题描述】:

我有一个字符串(或单词列表)。我想创建每个可能的单词对组合的元组,以便将它们传递给 Counter 以进行字典创建和频率计算。频率按以下方式计算:如果该对存在于一个字符串中(无论顺序如何,或者它们之间是否有任何其他单词),频率 = 1(即使 word1 的频率为 7,word2 的频率为 3)一对 word1 和 word2 仍然是 1)

我正在使用循环创建所有对的元组但卡住了

tweetList = ('I went to work but got delayed at other work and got stuck in a traffic and I went to drink some coffee but got no money and asked for money from work', 'We went to get our car but the car was not ready. We tried to expedite our car but were told it is not ready')

words = set(tweetList.split())
n = 10
for tweet in tweetList:

    for word1 in words:
        for word2 in words:
            pairW = [(word1, word2)]

            c1 = Counter(pairW for pairW in tweet)

c1.most_common(n)

但是,输出很奇怪:

[('k', 1)]

它似乎不是单词而是迭代字母

如何解决这个问题?使用 split() 将字符串转换为单词列表?

另一个问题:如何避免创建重复的元组,例如:(word1,word2)和(word2,word1)?枚举?

作为输出,我希望有一个字典,其中键 = 所有单词对(但请参阅重复的注释),值 = 列表中一对的频率

谢谢!

【问题讨论】:

  • 你应该指出你期望的输出。
  • for tweet in tweetlist 会遍历原始字符串中的字符,这似乎毫无意义。在它上面调用split 不会导致它变成一个列表
  • tweetlist 是 2 个字符串的列表
  • ('work','work') 这样的配对呢?那一对有序的词——你要数这样的词对吗?
  • @Toly -- 我明白了,我滚动到最后但错过了中间的逗号。狡猾地说,它是一个字符串的元组。但是然后- 调用split 是没有意义的。元组没有拆分方法。

标签: python tuples counter std-pair


【解决方案1】:

我想知道这是不是你想要的:

import itertools, collections

tweets = ['I went to work but got delayed at other work and got stuck in a traffic and I went to drink some coffee but got no money and asked for money from work',
          'We went to get our car but the car was not ready. We tried to expedite our car but were told it is not ready']

words = set(word.lower() for tweet in tweets for word in tweet.split())
_pairs = list(itertools.permutations(words, 2))
# We need to clean up similar pairs: sort words in each pair and then convert
# them to tuple so we can convert whole list into set.
pairs = set(map(tuple, map(sorted, _pairs)))

c = collections.Counter()

for tweet in tweets:
    for pair in pairs:
        if pair[0] in tweet and pair[1] in tweet:
            c.update({pair: 1})

print c.most_common(10)

结果是:[(('a', 'went'), 2), (('a', 'the'), 2), (('but', 'i'), 2), (('i', 'the'), 2), (('but', 'the'), 2), (('a', 'i'), 2), (('a', 'we'), 2), (('but', 'we'), 2), (('no', 'went'), 2), (('but', 'went'), 2)]

【讨论】:

  • 看起来不错。由于只有 2 个字符串,因此最大频率为 2。需要检查 N = 100 以查看其余字符串是否为 1。我只是好奇为什么我的方式如此偏离。
  • 好吧,比较一下你和我的版本,你就知道为什么了。首先,pairW for pairW in tweet 刚刚生成了一个推文字母列表(隐藏您之前定义的 pairW 变量)。然后c1 总是被替换为新版本,而不是整个循环都相同。您还尝试拆分元组 - tweetList.split() - 同时生成单词列表有点复杂。
  • 太棒了!我检查了一下,它有效。因为只有 2 个字符串,所以频率应该是从 2 到 0。谢谢你,萨沙:)
【解决方案2】:

tweet 是一个字符串,因此Counter(pairW for pairW in tweet) 将计算tweet 中字母的频率,这可能不是您想要的。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-08-22
    • 1970-01-01
    • 1970-01-01
    • 2020-02-07
    相关资源
    最近更新 更多