Python 加入给定列表中的一组单词

Python 加入给定列表中的一组单词,python,Python,我的问题看起来很简单,但我想不出一个干净(高效)的解决方案 我有一个对应于常见词组的元组列表: ngrams = [("data", "scientist"), ("machine", "learning"), ("c", "+"), ("+", "+"), ("c", "+", "+"), ("research", "and", "development"), ("resea

我的问题看起来很简单,但我想不出一个干净(高效)的解决方案

我有一个对应于常见词组的元组列表:

ngrams = [("data", "scientist"),
          ("machine", "learning"),
          ("c", "+"),
          ("+", "+"),
          ("c", "+", "+"),
          ("research", "and", "development"),
          ("research", "and")]
还有一句话:

"i am a data scientist . i do machine learning and c + + but no deep learning . i like research and development"
我想将常见的词组合并到一个标记中,如下所示:

"i am a data_scientist . i do machine_learning and c_+_+ but no deep_learning . i like research_and_development"
我相信有一种优雅的方式可以做到这一点,但我一直没有找到任何


如果只有两个元组,那么在
zip(句子,句子[:1]
上迭代就可以了,但是我在
ngrams
中有多达8个元组,这个解决方案是不易处理的!

您可以从
ngrams
中的单词中构建替换字符串列表:

replace = [" ".join(x) for x in ngrams]
然后,对于该列表中的每个元素,使用
str.replace

for r in replace:
    sentence = sentence.replace(r, r.replace(" ", "_"))

可能有一种更简单的方法,但对我来说似乎相对简洁易懂。

虽然Haldean Brown的答案更简单,但我认为这是一种更结构化的方法:

ngrams = [("data", "scientist"),
          ("machine", "learning"),
          ("c", "+"),
          ("+", "+"),
          ("c", "+", "+"),
          ("research", "and", "development"),
          ("research", "and")]
sent = """
    i am a data scientist . i do machine learning and c + + but no deep
    learning . i like research and development
"""

ngrams.sort(key=lambda x: -len(x))
tokens = sent.split()

out_ngrams = []
i_token = 0
while i_token < len(tokens):
    for ngram in ngrams:
        if ngram == tuple(tokens[i_token : i_token + len(ngram)]):
            i_token += len(ngram)
            out_ngrams.append(ngram)
            break
    else:
        out_ngrams.append((tokens[i_token],))
        i_token += 1

print(' '.join('_'.join(ngram) for ngram in out_ngrams))
ngrams
排序后:

[('c', '+', '+'),
 ('research', 'and', 'development'),
 ('data', 'scientist'),
 ('machine', 'learning'),
 ('c', '+'),
 ('+', '+'),
 ('research', 'and')]
这需要尝试在
(“c”,“+”,“+”)
之前应用
(“c”,“+”)
(或者,一般来说,尝试在其前缀之前应用一个序列)。实际上,像
[('c','+'),('+','a')]
这样的非贪婪的东西可能比
[('c','+','a'),]更可取
,但这是另一个故事

s = ''
seq = ("c", "+", "+")
print(s.join(seq))
有关联接方法的详细信息: Python文档


ttps://docs.python.org/3/library/stdtypes.html?highlight=join#str.join

您想实现什么?如果您想实现TF-IDF的一个变体,请检查Python的sklearn包
joined\ngrams=[''.'.join(t)for t in ngrams]
那没用。我想要的是将输入中的任何给定句子转换成一个句子,在这个句子中,出现在
ngrams
中的多组单词被连接起来。这很有效,非常感谢!我想我被卡住了,因为我试图找到一个能在O(len(句子))中工作的解决方案通过在一组中旋转
ngram
。我仍然认为这是可能的,但可能不那么优雅!我认为这可以在O(len(句子)*len(最长的ngram))中完成,方法类似于一本字典,它将一个族中每个最短的ngram映射到它的族(其中,族是一个带有公共前缀的ngram列表)。
s = ''
seq = ("c", "+", "+")
print(s.join(seq))