Python:获取Python中获得的计数总和

时间:2012-08-03 17:21:31

标签: python count sum

我是一个每天都在与Python斗争的初学者。我有一个大型数据集,在第二列中有动物名称。我有一个程序,用它的名字来计算每只动物的数量(每行有1个动物名称和1个“计数”数据)。我试图得到我使用Python获得的那些计数数据的总和,但我无法做到这一点。我到目前为止的代码是:

import csv, collections

reader=csv.reader(open('C:\Users\Owl\Data.txt','rb'), delimiter='\t')

counts=collections.Counter()

for line in reader:
   Name=line[1]
   counts[Name]+=1

for (Name, count) in sorted(counts.iteritems()):
   Output=list('%s' % count) #Make output string to a list
   Sum=sum(Output) # Sum function requires a list
   print 'Total kinds of Animals: %s' % Sum

我收到错误" File "sum_count.py", line 17, in <module> Sum=sum(Output) # Sum function requires a list TypeError: unsupported operand type(s) for +: 'int' and 'str'".

到目前为止我所知道的是因为sum显然需要输入类型作为列表,我将计数数据(字符串)转换为列表,但是当我Output=list('%s' % count)时,似乎所有超过2位数的计数数据都被拆分。例如,当我打印输出时,它将是这样的:

['1', '6', '3']
['3']
['1', '8', '5', '9']
['7', '9']

而不是

['163']
['3']
['1859']
['79']

我想在这里做的是获得这些元素的单一“总和”。在这里,它将是4.四种动物。

我想这可能是我收到上述错误的原因。我可能错了,但有人可以帮我解决这个问题吗?感谢您的帮助!

4 个答案:

答案 0 :(得分:3)

我认为您不需要使用sum

试试这个:

for (Name, count) in sorted(counts.iteritems()):
    print 'Species total: %s' % count

或者,可能更好:

for (Name, count) in sorted(counts.iteritems()):
    print 'Total for species %s: %s' % (Name, count)

sum适用于有数字列表并希望查找该数字列表的总和的情况。 您已经使用counts收集了每只动物的总数 - 您只需要显示它。

修改

总结计算的动物总数,您可以这样做:

total = sum(counts.values())
print 'Total number of animals: %d' % total

修改2

计算的动物种类数量只是counts字典的长度:

print 'Number of kinds of animals: %d' % len(counts)

答案 1 :(得分:2)

(重写以下评论讨论;原始答案只是指出OP试图添加字符串。)

其他答案有更多的扩展机会(因此我会推荐它们),但如果您只想要快速计算动物类型的数量,您可以简单地计算行数在文件中,并使用您对文件结构的了解。例如,如果你的csv文件有一个像Name, Count, etc.这样的标题,那么下一行只跟着你感兴趣的数据,那么动物的数量就是文件中非空行的数量减1为标题。然后,您可以使用以下代码打印计数:

print sum(1 for line in open('test.csv') if line.strip() != '') - 1

以下是该代码的每个部分的作用:

  • sum()在其中添加列表的所有元素。在这种情况下,里面没有列表,而是一个生成器表达式,这里可以认为是一个没有进入内存的列表。
  • 1 for line in open('test.csv')这是生成器表达式的第一部分。它本身会生成一个生成器,其长度为test.csv中的行数,其中每个元素都是1(如果文件中有五行,则类似列表将为[1,1,1,1,1] )。
  • if line.strip() != ''这是生成器表达式的第二部分。它确保1仅在生成器上添加任何内容时才会添加到生成器中。
  • -1从值sum(...)中减去一个,以忽略csv的标题

嗯,我希望在某种程度上有所帮助,我应该重申,这种方法只是一种快速而肮脏的方法;例如,如果您正在对数据进行其他操作,则不会使用它。

答案 2 :(得分:2)

获取计数

我认为问题源于你将“计数”与“总数”区分开来的事实。 “count”该项目的总出现次数。此外,您滥用collections.Counter(),它可以让您的作业更容易批次。以下是我认为您要实现的目标的编码示例:

counts = collections.Counter(line[1] for line in reader if len(line) > 1)
#Now all the occurrences of each item are summed up, AND ordered by number of occurrences

print "Total number of animals: %d" % len(counts)
#This is what I THINK you are trying to do. 

此外:

for name, number in counts.items():
    print "# of %s: %d" % (name, number)

关于你的'TypeError`:

您有一个字符串列表,而不是整数列表。

一个例子:

mylist = ['1', '2', '3']

所有sum()执行的操作都是对iterable执行累积添加,类似于:

total = 0
for item in mylist:
    total = total + item

在这种情况下,totalint(值0),itemstr(值'1')。 Python不知道如何处理0 + 'string'

答案 3 :(得分:0)

首先,您使用Counter对象,但仅将其用作defaultdict的替代。 如果你想用它来做你的计数你可以通过你这样的输入(假设物种出现不止一次,你想知道每个物种出现的频率):

counts = collections.Counter(map(lambda item: item[0], reader))

但是如果你想计算所有动物的总和(不论种类),你必须在第一个循环中添加该数量。正如其他人所说的,因为你正在阅读字符串,所以首先必须从该数字中得出一个整数。

import csv

reader=csv.reader(open('in','rb'), delimiter='\t')

counts = dict()

for data in reader:
    animal = data[1]
    if animal not in counts:
        counts[animal]= 1
    else:
        counts[animal]+= 1

for animal in counts:
    print 'Animals of scpecies %s: %s' % (animal, counts[animal])   

print 'Species total: %s' % len(counts)
print 'All animals: %s' % sum(counts.values())