【问题标题】:How to store CSV data in a Nested Dictionary that has a dictionary and a list?如何将 CSV 数据存储在具有字典和列表的嵌套字典中?
【发布时间】:2014-09-17 23:46:06
【问题描述】:

我有以下 CSV 数据,

Rule1,Status1,1
Rule1,Status2,1
Rule1,Status3,1
Rule1,Status4,2
Rule2,Status1,2
Rule2,Status2,1
Rule2,Status3,1
Rule2,Status4,3

我有一个独特的规则(第一列)存储在一个名为规则的列表中。我希望我的字典如下所示:

DictionaryFull = {
                  'Rule1' : {1 : [Status1, Status2, Status3], 2 : [Status4]},
                  'Rule2' : {1 : [Status2, Status3], 2 : [Status1], 3 : [Status4]}
                 }

这是我尝试过的:

openfile = ('data.csv', 'rU')
finalfile = csv.reader(openfile, delimiter=',')

FullDictionary = {}

for row in finalfile:
  for j in range (0, 300): #300 number of rules 
    if Rules[j] not in FullDictionary:
        for i in range(1, 71): #These are third column numbers 1 - 71 
            if i == int(row[2]) and row[0] == Rules[j]:
                FullDictionary = {Rules[j] : { i : [].append[row[1]}}
                    print FullDictionary

但我得到以下结果:

{'Rule1': {1 : None}} and so on

我做错了吗?如何完成将字典与另一个字典和列表一起使用的任务。

我试过这个:

def something():
    full_dictionary = {}
    with open(DataFilePath) as f:
        reader = csv.reader(f)
        for row in reader:
            rule = row[2], status = row[0], num = int(row[5])
            r = full_dictionary.setdefault(rule, {})
            r.setdefault(num, []).append(status)

    print full_dictionary

错误:ValueError: I/O operation on closed file

【问题讨论】:

    标签: python list python-2.7 csv dictionary


    【解决方案1】:

    关于使用collection.defaultdict

    import csv
    from collections import defaultdict
    
    full_dictionary = defaultdict(lambda: defaultdict(list))
    with open('data.csv') as f:
        reader = csv.reader(f)
        for rule, status, num in reader:
            full_dictionary[rule][num].append(status)
    
    print full_dictionary
    

    输出:

    defaultdict(<function <lambda> at 0x00000000025A6438>, {
        'Rule2': defaultdict(<type 'list'>, {
            '1': ['Status2', 'Status3'],
            '3': ['Status4'],
            '2': ['Status1']
         }),
         'Rule1': defaultdict(<type 'list'>, {
             '1': ['Status1', 'Status2', 'Status3'],
             '2': ['Status4']
         })
    })
    

    如果您不想使用defaultdict,则必须注意新密钥。

    例如,使用dict.setdefault:

    import csv
    
    full_dictionary = {}
    with open('data.csv') as f:
        reader = csv.reader(f)
        for rule, status, num in reader:
            r = full_dictionary.setdefault(rule, {})
            r.setdefault(num, []).append(status)
    
    print full_dictionary
    

    输出:

    {'Rule1': {'1': ['Status1', 'Status2', 'Status3'], '2': ['Status4']},
     'Rule2': {'1': ['Status2', 'Status3'], '2': ['Status1'], '3': ['Status4']}}
    

    【讨论】:

    • 如果我在 csv 中有超过 3 列怎么办?并且出现错误“I/O operation on closed file”
    • @GravityM,你的意思是可以有任意的列号吗?那么,应该将哪一列放入列表中呢?
    • @GravityM,我在答案中使用了with statement。它在块的末尾关闭文件。如果你想对文件做点什么,在with语句块内做。
    • 是的,有行[0]、[1]、[2]、[3]、[5]、[4]。我只走[1]行[2]和路[4]。
    • @GravityM,将for rule, status, num in reader: 替换为for row in reader: rule, status, num = row[1], row[2], row[4]
    【解决方案2】:

    list.append 返回 None,因此您的赋值 Rules[j] = [].append([row[1]) 设置为 Rules[j] = None

    修改为:

    FullDictionary = {Rules[j] : { i : [row[1]}}
    

    old_value = Rules[j].get(i, [])
    old_value.append(row[1])
    

    取决于您希望达到的目标。

    【讨论】:

    • 它有效,但它只显示一种状态。 {'Rule1': {1: ['Status1']}} 并在下一个打印状态2。等等...但我想要 ['Status1', 'Status2']
    猜你喜欢
    • 1970-01-01
    • 2021-08-09
    • 2020-12-15
    • 1970-01-01
    • 2023-03-11
    • 1970-01-01
    • 2022-12-05
    • 2021-08-20
    • 2012-05-21
    相关资源
    最近更新 更多