software - python tutorial




पायथन सिंटेक्सएर्रर के बजाय टाइप-इयरर को क्यों बढ़ाता है? (2)

इंडेक्सिंग ऑपरेशन में कोलन का उपयोग करने से एक slice ऑब्जेक्ट उत्पन्न होता है , जो कि हैशेबल नहीं है।

शुद्ध रूप से जिज्ञासा के लिए एक प्रश्न। यह स्पष्ट रूप से अमान्य सिंटैक्स है:

foo = {}
foo['bar': 'baz']

यह स्पष्ट है कि क्या हुआ, डेवलपर ने शब्दकोष की परिभाषा से एक पंक्ति आगे बढ़ाई, लेकिन इसे शाब्दिक शब्दकोश घोषणा से असाइनमेंट सिंटैक्स में नहीं बदला (और इसके परिणामस्वरूप उपयुक्त रूप से नकली किया गया है)।

लेकिन मेरा सवाल यह है कि पायथन TypeError: unhashable type क्यों TypeError: unhashable type बजाय यहां TypeError: unhashable type नहीं है? यह किस प्रकार का हैश करने का प्रयास कर रहा है? बस यह कर रहा है:

'bar': 'baz'

एक वाक्य रचना है, जैसा कि यह है:

['bar': 'baz']

इसलिए मैं यह नहीं देख सकता कि किस प्रकार का निर्माण किया जा रहा है जो कि उपलब्ध नहीं है।


मैं केवल इग्नासियो उत्तर (जो महान है) में कुछ विवरण जोड़ना चाहता हूं और मुझे समझने में कुछ समय लगता है और मेरे जैसे लोगों के लिए जो इसे नहीं मिला (मैं केवल एक ही हो सकता हूं जो मुझे नहीं मिला क्योंकि मैंने किया नहीं किसी को यह नहीं पूछना कि मैं समझ नहीं पाया लेकिन कैसे जानता है :)):

पहली बार मुझे आश्चर्य है कि क्या टुकड़ा है? शब्दकोश अनुक्रमण टुकड़ा करने की क्रिया स्वीकार नहीं करते?

लेकिन यह मेरी ओर से एक बेवकूफी भरा सवाल है क्योंकि मैं भूल जाता हूं कि अजगर गतिशील होता है (मैं कितना बेवकूफ हूं) इसलिए जब अजगर कोड को संकलित करता है तो मुट्ठी समय अजगर को पता नहीं चलता कि क्या foo एक शब्दकोष या एक सूची है ताकि कोई भी पढ़े इस तरह की अभिव्यक्ति ['फू': 'बार'] एक स्लाइस के रूप में, यह जानने के लिए कि आप बस कर सकते हैं:

def f():
    foo = {}
    foo['bar':'foo']

और dis मॉड्यूल का उपयोग करके आप देखेंगे कि अभिव्यक्ति 'bar':'foo' स्वचालित रूप से एक स्लाइस में परिवर्तित हो गई है:

dis.dis(f)
  2           0 BUILD_MAP                0
              3 STORE_FAST               0 (foo)

  3           6 LOAD_FAST                0 (foo)
              9 LOAD_CONST               1 ('bar')
             12 LOAD_CONST               2 ('foo')
             15 SLICE+3             <<<<<<<<<<<<<<<<<<<<<< HERE!!!!!!            
             16 POP_TOP             
             17 LOAD_CONST               0 (None)
             20 RETURN_VALUE   

पहली बार जब मैंने स्वीकार किया तो मैंने इस बारे में नहीं सोचा था और मैं सीधे अजगर के स्रोत कोड पर गया था, यह समझने की कोशिश कर रहा था कि, क्योंकि सूची का __getitem__ किसी शब्दकोश के __getitem__ की तरह नहीं है, लेकिन अब मैं इसे क्यों नहीं समझ सकता हूँ क्योंकि अगर यह स्लाइस और स्लाइस अस्वास्थ्यकर हैं यह unhashable type , इसलिए यहां शब्दकोश __getitem__ का कोड है:

static PyObject *
dict_subscript(PyDictObject *mp, register PyObject *key)
{
    PyObject *v;
    long hash;
    PyDictEntry *ep;
    assert(mp->ma_table != NULL);   
    if (!PyString_CheckExact(key) ||                // if check it's not a string 
        (hash = ((PyStringObject *) key)->ob_shash) == -1) {
        hash = PyObject_Hash(key);    // check if key (sliceobject) is hashable which is false 
        if (hash == -1)
            return NULL;
    } 
    ....

आशा है कि यह मेरे जैसे कुछ लोगों को इग्नासियो की महान प्रतिक्रिया को समझने में मदद कर सकता है, और अगर मुझे सिर्फ इग्नासियो के उत्तर की नकल करने पर खेद है :)





python