【问题标题】:Counting the number of duplicates in a list [duplicate]计算列表中重复项的数量[重复]
【发布时间】:2019-02-04 23:54:49
【问题描述】:

我正在尝试构建此函数,但我不知道如何停止该函数多次计算相同的重复项。有人可以帮帮我吗?

def count_duplicates(seq): 

    '''takes as argument a sequence and
    returns the number of duplicate elements'''

    fir = 0
    sec = 1
    count = 0
    while fir < len(seq):
        while sec < len(seq):
            if seq[fir] == seq[sec]:
                count = count + 1
            sec = sec + 1
        fir = fir + 1
        sec = fir + 1
    return count 

在:count_duplicates([-1,2,4,2,0,4,4])

输出:4

这里失败了,因为输出应该是3

【问题讨论】:

  • 你如何定义“重复元素的数量”? 2号有两次,4号有3次。你在计算最频繁元素的出现次数吗?
  • 您尝试过使用Counter 了吗?
  • @AlexTaylor 和 zvone 有一个重复的 2 和两个重复的 4,总共是 3。
  • @zvone 如果相同的值在一个序列中出现多次,我将调用它的所有副本,除了第一个:重复。
  • 因此,如果您通过 count_duplicatesseq[1,1,1,1],它将返回 3+2+1=6。您可以通过将break 放在count = count + 1 行之后,仅计算每个项目的第一个重复项来解决此问题。但最好使用一种更有效的技术。

标签: python list count duplicates sequence


【解决方案1】:

您可以从列表中创建一个set,它会自动删除重复项,然后计算创建的集合与原始列表的长度之差。 像这样:

def count_duplicates(seq): 

    '''takes as argument a sequence and
    returns the number of duplicate elements'''

    return len(seq) - len(set(seq))

res = count_duplicates([-1,2,4,2,0,4,4])
print(res)  # -> 3

如果您不被允许或不想使用任何内置快捷方式(无论出于何种原因),您可以采用 long(er) 方式:

def count_duplicates2(seq): 

    '''takes as argument a sequence and
    returns the number of duplicate elements'''

    counter = 0
    seen = set()
    for elm in seq:
        if elm in seen:
            counter += 1
        else:
            seen.add(elm)
    return counter

res = count_duplicates2([-1,2,4,2,0,4,4])
print(res)  # -> 3

最后,就您的代码而言,@AlanB 在his answer 中很好地概述了它的问题。我选择不打扰更正您的代码,因为在我看来这是一个XY Problem。很明显,您具有某种编程背景,但您复杂的 while 循环只是不是在 Python 中完成的方式

【讨论】:

  • 这行得通,但你知道如何在不使用'set'的情况下做到这一点吗?
  • @Cassy 我更新了我的解决方案。看看吧。
  • @downvoter 我可以就可以改进的地方提供一些反馈吗?
  • 我已经投了赞成票,但也许可以解释为什么 Cassy 的代码给出了错误的答案。我会删除我对这个问题的评论。
  • 顺便说一句,您的替代方案仍然使用一组。 ;) Cassy 可能还没有学过套装,所以她不能在这个作业中使用它们。
【解决方案2】:

Ev 的解决方案。 Kounis 是最简单的,我认为你应该使用它。但是,如果您想坚持自己的代码,这就是它不起作用的原因:

使用您复杂的while 循环,您基本上会说“对于我列表中的每个项目,当您找到重复项时增加count”,这基本上就是您想要的。但由于您有两个“4 个重复项”,它会增加 count 一个额外的时间。

seq=[-1,2,4,2,0,4,4]
fir = 0
sec = 0
count = 0
print "Pairs of duplicates: "
for fir, item1 in enumerate(seq):
    for sec, item2 in enumerate(seq):
        if fir < sec and seq[fir] == seq[sec] :
            count+=1
            print(fir, sec)
    
print "Number of duplicates: ", count 

哪些输出:

Pairs of duplicates: 
(1, 3)
(2, 5)
(2, 6)
(5, 6)
Number of duplicates:  4

(5,6) 对不正确。

要解决此问题,只需在您的 if 语句中添加一个条件,以防止对一个项目进行两次比较:

seq=[-1,2,4,2,0,4,4]
fir = 0
sec = 0
count = 0
duplicates=[]
print "Pairs of duplicates: "
for fir, item1 in enumerate(seq):
    for sec, item2 in enumerate(seq):
        if fir < sec and seq[fir] == seq[sec] and seq[fir] not in duplicates:
            count+=1
            print(fir, sec)

    duplicates.append(seq[fir])

print "Number of duplicates: ", count

输出期望的结果:

Pairs of duplicates: 
(1, 3)
(2, 5)
(2, 6)
Number of duplicates:  3

再一次,做

len(seq)-len(set(seq))

更简单,效果也很好。

编辑:

我意识到我的示例中没有使用 while 循环。

def count_duplicates(seq): 

    fir = 0
    sec = 0
    count = 0
    duplicates=[]
    print "Pairs of duplicates: "
    while fir < len(seq):
        while sec < len(seq):
            if fir < sec and seq[fir] == seq[sec] and seq[fir] not in duplicates:
                count += 1
                print(fir, sec)
            sec += 1
        duplicates.append(seq[fir])
        fir += 1
        sec = 0
    return count 


c=count_duplicates([-1,2,4,2,0,4,4])
print "Number of duplicates: ", c

【讨论】:

  • 是的,你对 Cassy 代码的 mod 看起来不错(我在手机上,所以测试起来并不容易)。但是我的建议是在检测到第一个骗子后立即退出内部循环,这更简单、更有效。 ;) 顺便说一句,如果你不想从零开始计数,你可以给 enumerate start arg。您可以在内部循环中使用它,但当然您还需要遍历seq 的一部分。
  • 我同意你的观点,我只是想让解决方案尽可能简单。我应该编辑我的答案吗?
  • 简单就是好。 :) 我的猜测是 Cassy 将无法使用enumerate,在她接受 Python 教育的这个阶段,即使是您的其他解决方案也可能有点太先进了。因此,如果它更简单,请随意添加另一个版本。
  • FWIW,我赞成这个答案,因为它解释了为什么 OP 的代码给出了错误的答案,并展示了一种修改该代码以获得正确计数的方法。当然,有更好的方法来完成这项任务,但恕我直言,获得这样的反馈也非常有用,尤其是当你还在学习如何编程时。
  • 我第一次尝试就遇到了这个问题
【解决方案3】:

使用 Pandas 的方法。此方法适用于具有重复项的大型列表。

data = [-1,2,4,2,0,4,4]
import pandas as pd
df = pd.DataFrame({'data':data}) #Loading the data as Data Frame
print(df[df1==False]) #Printing Non-Duplicated Values
   data
0    -1
1     2
2     4
4     0
print(df[df1==False].count()) #Taking count of Non-Duplicate Values
data    4
dtype: int64

【讨论】:

    猜你喜欢
    • 2012-09-05
    • 1970-01-01
    • 2016-03-04
    • 1970-01-01
    • 2015-05-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多