আপনি কীভাবে পাইথনে নেস্টেড ডিক তৈরি করেন?


149

আমার কাছে দুটি সিএসভি ফাইল রয়েছে: 'ডেটা' এবং 'ম্যাপিং':

  • 'ম্যাপিং' ফাইল 4 টি কলাম আছে: Device_Name, GDN, Device_Type, এবং Device_OS। চারটি কলামই জনবহুল।
  • 'ডেটা' ফাইলটিতে একই কলাম রয়েছে, Device_Nameকলাম পপুলেটে এবং অন্যান্য তিনটি কলাম ফাঁকা রয়েছে।
  • আমি আমার পাইথন কোড উভয় ফাইল এবং প্রত্যেকের জন্য খুলতে চান Device_Name, তথ্য ফাইলে তার মানচিত্র GDN, Device_Typeএবং Device_OSম্যাপিং ফাইল থেকে মান।

আমি যখন মাত্র 2 টি কলাম উপস্থিত থাকি তখন ডিকটি কীভাবে ব্যবহার করতে হয় তা আমি জানি (3 টি কলাম ম্যাপ করার প্রয়োজন হয় তবে কীভাবে এটি সম্পাদন করতে হয় তা আমি জানি না।

নিম্নলিখিত কোডটি ব্যবহার করে আমি ম্যাপিংটি সম্পাদন করার চেষ্টা করেছি 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)

এটি ফিরে আসে Attribute Error

কিছু গবেষণা করার পরে, আমি মনে করি আমার একটি নেস্টেড ডিক তৈরি করা দরকার, তবে এটি কীভাবে করবেন তা সম্পর্কে আমার কোনও ধারণা নেই।


Device_Nameকলাম হ'ল উভয় ফাইলে চাবিকাঠি, এই কীতে আমি ডিভাইস_এস, জিডিএন এবং ডিভাইস_টাইপ মানগুলি ম্যাপিং ফাইল থেকে ডেটা ফাইলে মানচিত্র করতে চাই।
এটমস

আপনি কি কিছু করতে সক্ষম হতে চান row[27] = x[row[11]]["Device_OS"]?
জান্নে কারিলা


এটি অগত্যা নেস্টেড ডিকের প্রয়োজন নেই। আপনি পান্ডাস, পঠন_সিএসভি ব্যবহার করতে পারেন, সূচি তৈরি Device_Nameকরতে পারেন, তারপরে আপনি সরাসরি joinতাদের সূচীতে দুটি ডেটাফ্রেম করতে পারেন Device_Name
স্মি

উত্তর:


307

নেস্টেড ডিক্ট একটি অভিধানের মধ্যে একটি অভিধান। খুব সহজ একটি জিনিস।

>>> d = {}
>>> d['dict1'] = {}
>>> d['dict1']['innerkey'] = 'value'
>>> d
{'dict1': {'innerkey': 'value'}}

নেস্টেড অভিধান তৈরির সুবিধার্থে আপনি প্যাকেজ defaultdictথেকে একটি ব্যবহার করতে পারেন collections

>>> 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

আপনার মন্তব্য অনুযায়ী :

কোডের উপরে হতে পারে প্রশ্নটি বিভ্রান্ত করছে। সংক্ষেপে আমার সমস্যা: আমার কাছে দুটি ফাইল রয়েছে a.csv b.csv, a.csv এর 4 টি কলাম ijkl রয়েছে, বিসিএসভিতেও এই কলামগুলি রয়েছে। আমি এই সিএসভি'র জন্য কী কলামগুলির ধরণ। jkl কলামটি a.csv এ খালি কিন্তু বিসিএসভিতে জনবহুল। আমি জে কে এল কলামগুলির মানগুলিকে ব্রেএসএসভি থেকে এ সি এস ফাইলে মূল কলাম হিসাবে i` ব্যবহার করে মানচিত্র তৈরি করতে চাই

আমার পরামর্শ কিছু হবে মত এই (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:]))

তবে দয়া করে মনে রাখবেন যে CSV ফাইলগুলি পার্স করার জন্য একটি সিএসভি মডিউল রয়েছে


কোডের উপরে হতে পারে প্রশ্নটি বিভ্রান্ত করছে। সংক্ষেপে আমার সমস্যা: আমার 2 টি ফাইল রয়েছে a.csv b.csv, a.csv4 টি কলাম রয়েছে i j k l, b.csvএছাড়াও এই কলামগুলি রয়েছে। iএই সিএসভি'র জন্য কী কলামগুলির ধরণ। j k lকলামটি ফাঁকা a.csvতবে জনবহুল b.csv। আমি j k lb.csv থেকে a.csv ফাইলে কী কলাম হিসাবে 'i` ব্যবহার করে কলামগুলির মানগুলি মানচিত্র করতে চাই ।
এটমস

64

আপডেট : নেস্টেড অভিধানের একটি স্বেচ্ছাসেবী দৈর্ঘ্যের জন্য, এই উত্তরে যান

সংগ্রহগুলি থেকে ডিফল্টডিক্ট ফাংশনটি ব্যবহার করুন।

উচ্চ কার্য সম্পাদন: ডেটা সেট বড় হলে "কী যদি ডিক না হয়" খুব ব্যয়বহুল।

স্বল্প রক্ষণাবেক্ষণ: কোডটি আরও পঠনযোগ্য করে তুলুন এবং সহজেই প্রসারিত করা যায়।

from collections import defaultdict

target_dict = defaultdict(dict)
target_dict[key1][key2] = val

3
from collections import defaultdict target_dict = defaultdict(dict) target_dict['1']['2']আমাকে দেয়target_dict['1']['2'] KeyError: '2'
28:58

1
এটি পাওয়ার আগে আপনাকে মূল্য নির্ধারণ করতে হবে।
জুনচেন

24

নেস্টনেস্ট্রি স্বেচ্ছাসেবী স্তরের জন্য:

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})})})

2
উপরের উত্তরটি একটি দুটি লাইন ফাংশন দিয়ে কী করে, আপনি এই উত্তর হিসাবে একটি এক-লাইন ল্যাম্বদা দিয়েও করতে পারেন ।
একিউম্যানাস

3

ডিফল্টডিক্টিক্ট এবং অনুরূপ নেস্টেড ডিক মডিউলগুলি ব্যবহার করার সময় এটি মনে রাখা গুরুত্বপূর্ণ nested_dictযে অস্তিত্বহীন কীটি অনুসন্ধান করা অনিচ্ছাকৃতভাবে ডিকটিতে একটি নতুন কী এন্ট্রি তৈরি করতে পারে এবং প্রচুর বিপর্যয় সৃষ্টি করতে পারে।

এখানে nested_dictমডিউল সহ পাইথন 3 উদাহরণ রয়েছে :

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
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.