पायथन: डिफॉल्टडिक्ट को डिक्टेट में बदलें


93

मैं एक डिफाल्ट कैसे बदल सकता हूं

number_to_letter
defaultdict(<class 'list'>, {'2': ['a'], '3': ['b'], '1': ['b', 'a']})

एक सामान्य तानाशाह बनना

{'2': ['a'], '3': ['b'], '1': ['b', 'a']}

11
dict(number_to_letter)
टिम पीटर्स

2
@TimPeters चूंकि यह वास्तव में एक अच्छी तरह से लिखित प्रश्न है, एक स्पष्ट शीर्षक के साथ (और खोजों में आसानी से दिखना चाहिए), भविष्य के संदर्भ के लिए यह एक मूल्य के रूप में डाल दिया जाएगा यदि हम एक उत्तर के रूप में पा सकते हैं जो बेहतर नहीं है .. ।
जॉन क्लेमेंट्स

इस उत्तर में मदद करनी चाहिए: stackoverflow.com/a/3031915/1628832
karthikr

1
@ जॉन्सल्स, अच्छी बात है, लेकिन DSM पहले ही कर चुका है - मुझे उम्मीद है कि उसका जवाब स्वीकार कर लिया जाएगा :-)
टिम पीटर्स

2
आप चाहिए (बेशर्म प्लग) द्वारा पॉप - 10k पर @TimPeters बधाई btw ... मुझे लगता है कि यह आप लंबे समय तक नहीं ले जाएगा था chat.stackoverflow.com/rooms/6/python कुछ बिंदु :) पर
जॉन क्लेमेंट्स

जवाबों:


124

आप बस कॉल कर सकते हैं dict:

>>> a
defaultdict(<type 'list'>, {'1': ['b', 'a'], '3': ['b'], '2': ['a']})
>>> dict(a)
{'1': ['b', 'a'], '3': ['b'], '2': ['a']}

लेकिन याद रखें कि एक डिफ़ॉल्ट एक तानाशाही है :

>>> isinstance(a, dict)
True

थोड़े अलग व्यवहार के साथ, इसमें जब आप एक कुंजी को एक्सेस करने की कोशिश करते हैं जो गायब है - जो आमतौर पर एक KeyError- एक को बढ़ाएगा - default_factoryबजाय इसे कॉल किया जाता है:

>>> a.default_factory
<type 'list'>

print aडिक्शनरी का डेटा साइड दिखाई देने से पहले आप यही देखते हैं ।

तो वास्तव में एक नई वस्तु बनाने के बिना अधिक तानाशाही व्यवहार वापस पाने के लिए एक और चाल को रीसेट करना है default_factory:

>>> a.default_factory = None
>>> a[4].append(10)
Traceback (most recent call last):
  File "<ipython-input-6-0721ca19bee1>", line 1, in <module>
    a[4].append(10)
KeyError: 4

लेकिन ज्यादातर समय यह परेशानी के लायक नहीं होता है।


मैं सिर्फ पायथन के साथ प्रोग्रामिंग सीखना शुरू करता हूं। क्या आप इसका उपयोग करने के बारे में अधिक बता सकते हैं default_factory? मुझे अभी कोई सुराग नहीं है कि क्या चल रहा है। माफ़ करना।
user2988464

और 'कीयर्रर ’क्या है?
user2988464

5
@ user2988464: आपने पहले ही उपयोग कर लिया है default_factory- यह वह फ़ंक्शन है जिसे आपने पास किया है जब आपने defaultdictपहली जगह में बनाया था , जैसे defaultdict(int)या defaultdict(list)। जब भी आप शब्दकोश में एक कुंजी को देखने की कोशिश करते हैं, जैसे a['3'], उदाहरण के लिए, एक सामान्य शब्दकोश में या तो आपको मूल्य मिलता है या यह एक KeyErrorअपवाद उठाता है (एक त्रुटि की तरह, आपको बता रहा है कि यह उस कुंजी को नहीं खोज सका)। लेकिन एक में defaultdict, यह आपके लिए एक नया डिफ़ॉल्ट मान बनाने के लिए default_factoryफ़ंक्शन को कॉल करता है (यह "डिफ़ॉल्ट" है ) आपके लिए। defaultdict
DSM

3
ध्यान दें कि Django के .items टेम्प्लेट प्रॉपर्टी डिफॉल्ट के साथ काम नहीं करेगी, यही वजह है कि मैं यहाँ समाप्त हुआ! इसलिए रूपांतरण का एक अच्छा कारण है
बेन

2
यह भी ध्यान दें कि pickle(एक फ़ाइल के लिए अजगर वस्तुओं को बचाने के लिए) कई परिस्थितियोंdefaultdict में एस नहीं संभाल सकता है
drevicko

28

यदि आपका डिफ़ॉल्ट निर्णय उदाहरण के लिए पुनरावर्ती है, तो:

from collections import defaultdict
recurddict = lambda: defaultdict(recurddict)
data = recurddict()
data["hello"] = "world"
data["good"]["day"] = True

अभी तक डिफाल्ड डिक्टेड को डिक्टेड में बदलने का एक और सरल तरीका jsonमॉड्यूल का उपयोग करना है

import json
data = json.loads(json.dumps(data))

और निश्चित रूप से, आपके डिफ़ॉल्ट में संतुष्ट सामग्री को समर्थित डेटा प्रकारों को सीमित करने की आवश्यकता होती है, लेकिन यह तब समस्या नहीं होनी चाहिए जब आप वर्ग या कार्यों को स्टोर करने का इरादा नहीं रखते हैं।


9
अच्छा विचार है, बहुत बुरा मेरा डेटा JSON को
अनुक्रमित

15

तुम भी एक पुनरावर्ती परिवर्तित करने के लिए एक पुनरावर्ती संस्करण चाहते हैं defaultdictएक करने के लिए dictआप निम्न कोशिश कर सकते हैं:

#! /usr/bin/env python3

from collections import defaultdict

def ddict():
    return defaultdict(ddict)

def ddict2dict(d):
    for k, v in d.items():
        if isinstance(v, dict):
            d[k] = ddict2dict(v)
    return dict(d)

myddict = ddict()

myddict["a"]["b"]["c"] = "value"

print(myddict)

mydict = ddict2dict(myddict)

print(mydict)

ठीक वैसा ही मुझे चाहिए! दुर्भाग्य से, मेरे डिफ़ॉल्ट में कुछ कुंजियाँ हैं जो बिना कस्टम एनकोडर के JSON अनुक्रमिक नहीं हैं (कुंजियाँ
टुपल्स हैं

1
अच्छा था। शब्दकोश की समझ का उपयोग करना पर्याप्त है यदि यह केवल दो परतों में गहरा हो (यानी defaultdict(lambda: defaultdict(int))): {k: dict(v) for k, v in foo.items()}
ggorlen
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.