你如何在Python中创build嵌套的字典?
我有2个CSV文件。 第一个是数据文件,另一个是映射文件。 映射文件有4列Device_Name GDN Device_Type Device_OS
这些也是数据文件中存在的需要处理的列。
数据文件包含Device_Name列填充的数据和其余3列空白的数据。 映射文件包含所有填充的列。 我想让我的Python代码打开这两个文件,并在数据文件中为每个设备名称映射其映射文件的GDN,Device_Type和Device_OS值。
我知道如何使用字典当只有2列(1是需要映射),但我不知道如何完成这3列需要映射。
以下是我试图完成Device_Type
映射的Device_Type
:
x = dict([]) with open("Pricing Mapping_2013-04-22.csv", "rb") as in_file1: file_map = csv.reader(in_file1, delimiter=',') for row in file_map: typemap = [row[0],row[2]] x.append(typemap) with open("Pricing_Updated_Cleaned.csv", "rb") as in_file2, open("Data Scraper_GDN.csv", "wb") as out_file: writer = csv.writer(out_file, delimiter=',') for row in csv.reader(in_file2, delimiter=','): try: row[27] = x[row[11]] except KeyError: row[27] = "" writer.writerow(row)
它返回Atribute Error
。
经过一番研究,我意识到我需要创build一个嵌套的字典,但我不知道如何做到这一点。 请帮我解决这个问题,或者在正确的方向推动我解决这个问题。
嵌套字典是字典中的字典。 一个非常简单的事情。
>>> d = {} >>> d['dict1'] = {} >>> d['dict1']['innerkey'] = 'value' >>> d {'dict1': {'innerkey': 'value'}}
您还可以使用collections
包中的defaultdict
来帮助创build嵌套字典。
>>> import collections >>> d = collections.defaultdict(dict) >>> d['dict1']['innerkey'] = 'value' >>> d # currently a defaultdict type defaultdict(<type 'dict'>, {'dict1': {'innerkey': 'value'}}) >>> dict(d) # but is exactly like a normal dictionary. {'dict1': {'innerkey': 'value'}}
你可以填充,但是你想要的。
我会推荐你的代码如下所示:
d = {} # can use defaultdict(dict) instead for row in file_map: # derive row key from something # when using defaultdict, we can skip the next step creating a dictionary on row_key d[row_key] = {} for idx, col in enumerate(row): d[row_key][idx] = col
根据你的评论 :
可能是上面的代码混淆了这个问题。 我的问题简而言之:我有2个文件a.csv b.csv,a.csv有4列ijkl,b.csv也有这些列。 我是这些csvs的关键列“。 jkl列在a.csv中是空的,但在b.csv中填充。 我想用'i`作为b.csv到a.csv文件的关键列来映射jk l列的值
我的build议是这样的(不使用defaultdict):
a_file = "path/to/a.csv" b_file = "path/to/b.csv" # read from file a.csv with open(a_file) as f: # skip headers f.next() # get first colum as keys keys = (line.split(',')[0] for line in f) # create empty dictionary: d = {} # read from file b.csv with open(b_file) as f: # gather headers except first key header headers = f.next().split(',')[1:] # iterate lines for line in f: # gather the colums cols = line.strip().split(',') # check to make sure this key should be mapped. if cols[0] not in keys: continue # add key to dict d[cols[0]] = dict( # inner keys are the header names, values are columns (headers[idx], v) for idx, v in enumerate(cols[1:]))
请注意,虽然,parsingCSV文件有一个CSV模块 。
更新 :对于任意长度的嵌套字典,去这个答案 。
使用集合中的defaultdict函数。
高性能:如果数据集很大,“如果键不在字典中”是非常昂贵的。
低维护:使代码更具可读性,并且可以轻松扩展。
from collections import defaultdict target_dict = defaultdict(dict) target_dict[key1][key2] = val
对于任意级别的嵌套:
In [2]: def nested_dict(): ...: return collections.defaultdict(nested_dict) ...: In [3]: a = nested_dict() In [4]: a Out[4]: defaultdict(<function __main__.nested_dict>, {}) In [5]: a['a']['b']['c'] = 1 In [6]: a Out[6]: defaultdict(<function __main__.nested_dict>, {'a': defaultdict(<function __main__.nested_dict>, {'b': defaultdict(<function __main__.nested_dict>, {'c': 1})})})
当使用defaultdict和类似嵌套的字典模块(如nested_dict)时,记住一个不存在的键可能会无意中在字典中创build一个新的键入并导致大量的破坏,这一点很重要。 这是一个nested_dict的Python3例子。
import nested_dict as nd nest = nd.nested_dict() nest['outer1']['inner1'] = 'v11' nest['outer1']['inner2'] = 'v12' print('original nested dict: \n', nest) try: nest['outer1']['wrong_key1'] except KeyError as e: print('exception missing key', e) print('nested dict after lookup with missing key. no exception raised:\n', nest) # instead convert back to normal dict nest_d = nest.to_dict(nest) try: print('converted to normal dict. Trying to lookup Wrong_key2') nest_d['outer1']['wrong_key2'] except KeyError as e: print('exception missing key', e) else: print(' no exception raised:\n') # or use dict.keys to check if key in nested dict. print('checking with dict.keys') print(list(nest['outer1'].keys())) if 'wrong_key3' in list(nest.keys()): print('found wrong_key3') else: print(' did not find wrong_key3')
输出是:
original nested dict: {"outer1": {"inner2": "v12", "inner1": "v11"}} nested dict after lookup with missing key. no exception raised: {"outer1": {"wrong_key1": {}, "inner2": "v12", "inner1": "v11"}} converted to normal dict. Trying to lookup Wrong_key2 exception missing key 'wrong_key2' checking with dict.keys ['wrong_key1', 'inner2', 'inner1'] did not find wrong_key3