2012-10-30 11 views
11

काम नहीं करता है मैं विंडोज पर पायथन 2.7.3 का उपयोग कर रहा हूं। मैंने क्लास विधि के रूप में __instancecheck__ जादू विधि को ओवरराइड करने का प्रयास किया। लेकिन मैं इसे काम नहीं कर सकता।क्लास विधि __instancecheck__

class Enumeration(int): 
    @classmethod 
    def __instancecheck__(cls, inst): 
     if type(inst) == cls: 
      return True 
     if isinstance(inst, int) and inst in range(0,10): 
      return True 
     return False 

print isinstance(1, Enumeration) # prints False 
print isinstance(1, Enumeration()) # prints True 

मुझे लगता है कि पहला प्रिंट स्टेटमेंट सत्य होगा। लेकिन ऐसा लगता है कि जादू विधि __instancecheck__ नहीं कहा जाता है। और मुझे नहीं पता कि दूसरा प्रिंट स्टेटमेंट क्यों काम कर सकता है क्योंकि isinstance को दूसरे पैरामीटर के रूप में कक्षा/प्रकार लेना चाहिए।

क्या किसी को पता है कि समस्या क्या है? धन्यवाद।

उत्तर

18

instancecheck एक metaclass में परिभाषित किया जाना चाहिए:

class Enumeration(type): 
    def __instancecheck__(self, other): 
     print 'hi' 
     return True 


class EnumInt(int): 
    __metaclass__ = Enumeration 

print isinstance('foo', EnumInt) # prints True 

कि क्यों है? इसी कारण से आपका दूसरा उदाहरण काम करता है। जब अजगर का मूल्यांकन करता है isinstance(A, B) यह B मान लिया गया एक वस्तु होने के लिए, अपने वर्ग के लिए लग रहा है और उस वर्ग पर __instancecheck__ कॉल:

isinstance(A, B): 
    C = class-of(B) 
    return C.__instancecheck__(A) 

लेकिन जब B एक वर्ग ही है, तो अपने वर्ग C एक वर्ग के एक वर्ग होना चाहिए, दूसरे शब्दों में, एक मेटा-क्लास!

5

डॉक्स कहते हैं:

ध्यान दें कि इन तरीकों एक वर्ग के प्रकार (metaclass) पर देखा जाता है। उन्हें वास्तविक वर्ग में वर्ग विधियों के रूप में परिभाषित नहीं किया जा सकता है। यह विशेष तरीकों के लुकअप के अनुरूप है जिसे उदाहरणों पर बुलाया जाता है, केवल इस मामले में उदाहरण स्वयं ही एक वर्ग है।

http://docs.python.org/2/reference/datamodel.html#customizing-instance-and-subclass-checks

+0

धन्यवाद। @ thg435 ने मुझे एक अच्छा उदाहरण दिया और अब मुझे पता है कि इसे कैसे प्राप्त किया जाए। – adarliu

संबंधित मुद्दे