我是python的新手,并尝试理解如何在csv.DictReader上使用过滤器函数来过滤csv文件中的行。 filter()可用于“可迭代”,据我所知,DictReader符合此definition。
然而,当我尝试
时f = open('file1.csv', 'r')
dialect = csv.Sniffer().sniff(f.read(1024))
f.seek(0)
reader = csv.DictReader(f, None, None, None, dialect)
filteredReader = filter(None, reader) #None will be replaced with my function
for i in filteredReader:
print(i)
我得到TypeError: normcase() argument must be str or bytes, not 'DictReader'
。
请注意,我不想在filepointer(e.g. here)上过滤,而是在解析的csv行上过滤。你知道怎么做吗?
答案 0 :(得分:2)
是的,DictReader()
可以用作可迭代的,并且可以与filter()
一起使用。
filter()
函数依次传递给每一行(字典),如果函数返回该行的True
,则传递给它:
>>> from io import StringIO
>>> import csv
>>> demo = StringIO('''\
... foo,bar,baz
... 42,88,131
... 17,19,23
... ''')
>>> reader = csv.DictReader(demo)
>>> def only_answers(row):
... return '42' in row.values()
...
>>> for row in filter(only_answers, reader):
... print(row)
...
{'baz': '131', 'bar': '88', 'foo': '42'}
答案 1 :(得分:0)
过滤器可以像您期望的那样使用DictReader。
假设你有这个csv文件:
numeral, English, Spanish
1, one, uno
2, two, dos
3, three, tres
4, four, quatro
5, five, cinco
(注意第2栏和第3栏中的前导空格)
你只想要奇数行:
>>> with open('/tmp/nums.csv') as f:
... print filter(lambda d: int(d['numeral'])%2, csv.DictReader(f))
[{' English': ' one', 'numeral': '1', ' Spanish': ' uno'}, {' English': ' three', 'numeral': '3', ' Spanish': ' tres'}, {' English': ' five', 'numeral': '5', ' Spanish': ' cinco'}]
请注意,前导空格来自我们的数据。好的,以这种方式尝试csv.Sniffer:
with open('/tmp/nums.csv') as f:
dialect = csv.Sniffer().sniff(f.read(1024))
f.seek(0)
print filter(lambda d: int(d['numeral'])%2, csv.DictReader(f, dialect=dialect))
# [{'numeral': '1', 'Spanish': 'uno', 'English': 'one'}, {'numeral': '3', 'Spanish': 'tres', 'English': 'three'}, {'numeral': '5', 'Spanish': 'cinco', 'English': 'five'}]
好的,sniffer
成功找到在方言中使用skipinitialspaces。