【问题标题】:Count how many double and triple characters appear in a list of strings计算字符串列表中出现了多少双字符和三字符
【发布时间】:2021-07-08 13:31:09
【问题描述】:

我有一长串字符串(以下只是 117k 列表的一个示例):

names = ['abc', 'aabc', 'aaabc', 'abbc', 'abxcc'] 

有没有一种有效的方法来计算其中出现了多少双字符(例如aa)或三字符(例如aaa)?我能想出的唯一方法是有一些循环如下:

for letter in alphabet:
  for word in strings_list:
    for letter in word
      etc.

但由于我的列表很大,我想知道是否有更有效的方法。

我还应该提到我的列表是中文的,因此我有大约 6600 个唯一字符

预期输出:

number_of_doubles = value_1
number_of_triples = value_2

更新:

澄清一下,像aaa 这样的字符串应该算作三倍而不是两个双倍

【问题讨论】:

  • 预期输出是什么?
  • 刚刚更新了我的问题以显示它!
  • 尝试提出任何解决方案并将其展示出来。这个问题太宽泛了,并没有真正显示any attempts
  • 这能回答你的问题吗? How to use re to find consecutive, repeated chars
  • zip(word[:-1],word[1:]) 将遍历一个可迭代对象中的连续对。你应该能够用它来组成你的答案。

标签: python string


【解决方案1】:

您可以编写一个自定义函数来进行累积计数并使用它来获得连续的双倍、三倍等:

def cumcount(word):
    counter = [1]
    for i, c in enumerate(word):
        if i == 0:
            continue
        if c == word[i-1]:
            counter[-1] += 1
        else:
            counter += [1]
    return counter

#for doubles
>>> {name: cumcount(name).count(2) for name in names}
{'abc': 0, 'aabc': 1, 'aaabc': 0, 'abbc': 1, 'abxcc': 1}

#for triples
>>> {name: cumcount(name).count(3) for name in names}
{'abc': 0, 'aabc': 0, 'aaabc': 1, 'abbc': 0, 'abxcc': 0}

【讨论】:

  • 除了这是半错误的,aaabc 有一个三倍,但它算作 2 个双倍
  • 是否应该计入双打?
  • 不应该,因为它是三重奏
  • 那么如果你有aaaa,那是一个三元组还是两个三元组?
  • 这种情况不会发生。最长的重复字符序列将是 3(因此您不必考虑 4+ 个字符)
【解决方案2】:

正则表达式 ([a-z])\1\1 将匹配任意字母 a-z 的三个重复,([a-z])\1 将匹配两个重复。

>>> re3 = re.compile(r"([a-z])\1\1")
>>> re2 = re.compile(r"([a-z])\1")
>>> names = ['abc', 'aabc', 'aaabc', 'abbc', 'abxcc']
>>> for n in names:
        print(n, len(re2.findall(n)), len(re3.findall(n)))

abc 0 0
aabc 1 0
aaabc 1 1
abbc 1 0
abxcc 1 0

您的问题不清楚aaa 是否算作2 匹配。如果没有,您可能需要进行一些补充检查。在正则表达式中这可能是不必要的棘手,因此您可能希望以其他方式消除重复计算。

【讨论】:

  • 我明白你的意思。它应该算作三重,我会在问题中澄清这一点
猜你喜欢
  • 2019-06-03
  • 1970-01-01
  • 2017-05-30
  • 1970-01-01
  • 2021-09-30
  • 2021-04-28
  • 1970-01-01
  • 1970-01-01
  • 2011-04-29
相关资源
最近更新 更多