操纵TSV文件

时间:2014-01-17 01:41:11

标签: python python-2.7 csv

我有一个.tsv文件数据文件,链接在这里: world bank data

我需要将数据读入数据结构(任何数据结构),只保留日期为“7/1/2000”或7/1/2010“的行,并且只保留原始19列中的7个。我对编程很陌生,但我认为这将是一项相当简单的任务。我这里的代码不完整:

import math
import csv
import re


fhand=open("world_bank_indicators.txt", "rU")
reader=csv.reader(fhand, dialect="excel", delimiter="\t",skipinitialspace=True)

data=dict()
mylist=list()

#doesn't print headers, however
for row in reader:
    if row[1]=="7/1/2000" or row[1]=="7/1/2010":
        print row[0], row[1], row[9], row[4], row[6], row[5], row[19]

UPDATE,使用dictreader的版本:

import math
import csv
import re

fhand=open("world_bank_indicators.txt", "rU")
reader=csv.reader(fhand, dialect="excel", delimiter="\t", lineterminator="\n")

reader=csv.DictReader(fhand, delimiter="\t")
myset=set()
mydict=dict()
mylist=list()

for row in reader:
    mydict["Date"]=row["Date"]

print mydict

但是,这似乎只写了一个条目{date:7/1/2010}到我的词典

所以,我明显的问题是:

1)这会打印我想要的数据的行和列,但是,它不会打印每列的标题 2)很明显,为了让我用数据进行任何计算,任何数据结构都没有添加任何内容

什么(非常明显,我确定)我在这里失踪的是什么?我怎样才能完成这两个简单的任务?

1 个答案:

答案 0 :(得分:1)

首先,要打印标题,您所要做的就是打印第一行的列,就像对所有7/1/2000行的列一样。例如:

headers = next(reader)
print row[0], row[1], row[9], row[4], row[6], row[5], row[19]

for row in reader:
    if row[1]=="7/1/2000" or row[1]=="7/1/2010":
        print row[0], row[1], row[9], row[4], row[6], row[5], row[19]

然而,实际上并没有产生TSV;你只需要用一个空格分隔列。另外,当然,你只是print将它们添加到stdout,而不是将它们写入文件。最简单的解决方案是使用csv.writer,方法与使用csv.reader

的方式相同
writer=csv.writer(outfile, dialect="excel", delimiter="\t",skipinitialspace=True)
# …
writer.writerow(row[0], row[1], row[9], row[4], row[6], row[5], row[19])

为了使其更清洁,并避免重复两次列列表,您可能需要使用operator.itemgetter,如下所示:

columns = 0, 1, 9, 4, 6, 5, 19
getter = operator.itemgetter(*columns)
# ...
writer.writerow(getter(row))

如果要存储值而不是将其写出来,只需将它们传递给append对象的list方法,而不是{{1}的writerow方法。对象。 (你可能也希望保持csv.writer。)

headers

你可以通过理解使这更加简洁:

headers = getter(next(reader))

data = []
for row in reader:
    if row[1]=="7/1/2000" or row[1]=="7/1/2010":
        data.append(getter(row))

如果您想使用data = [getter(row) for row in reader if row[1]=="7/1/2000" or row[1]=="7/1/2010"] ,则不会再按索引获取列,您将通过 name 获取这些列。此外,DictReader会自动使用标题行来计算这些名称。这是一个简化的例子。想象一下这是你的数据:

DictReader

让我们说我们只想要排名前10位的人的电子邮件。所以,这里是name,email,rank Joe,joe@example.com,7 Jim,jim@example.com,12 Jen,jane@example.com,2

reader

这里是reader = csv.reader(f) headers = next(reader) data = [row[1] for row in reader if int(row[2]) < 10]

DictReader

它可能不那么简洁,但它可能更具可读性。