2011-03-08 9 views
8

मुझे यह समझने में परेशानी हो रही है कि इन दावों में से पहला क्यों ठीक है और दूसरा एक त्रुटि उठाता है।सदस्यता परीक्षण एक सूची और एक सेट के लिए अलग कैसे है?

Traceback (most recent call last): 
    File "C:\Users\...\testSubject.py", line 34, in testIn 
    self.assertIn(Subject("A"), subject_set) 
AssertionError: <Subject: A> not found in set([<Subject: B>, <Subject: C>, <Subject: A>]) 

विषय कक्षा में समानता के लिए परीक्षण बस self.name == other.name है, और एक अन्य unittest में मुझे लगता है कि Subject("A") == Subject("A") सत्यापित करें:

subject_list = [Subject("A"), Subject("B"), Subject("C")] 
subject_set = set() 
subject_set.add(Subject("A")) 
subject_set.add(Subject("B")) 
subject_set.add(Subject("C")) 

self.assertIn(Subject("A"), subject_list) 
self.assertIn(Subject("A"), subject_set) 

यहाँ त्रुटि है। मैं वास्तव में यह नहीं समझ सकता कि विषय सूची में क्यों है और सेट में नहीं। आदर्श रूप में मैं विषय दोनों में होना चाहता हूं।

उत्तर

11

अभिव्यक्ति

Subject("A") in subject_list 

Subject.__eq__() पद्धति का उपयोग करके subject_list में प्रत्येक प्रविष्टि के Subject("A") की तुलना करेंगे। यदि यह विधि ओवरराइट नहीं की जाती है, तो यह हमेशा False लौटने के लिए डिफ़ॉल्ट होती है जब तक कि दो ऑपरेंड समान ऑब्जेक्ट नहीं हैं। उपरोक्त अभिव्यक्ति हमेशा False लौटाएगी यदि Subject में __eq__() विधि की कमी है, क्योंकि Subject("A") एक नया उदाहरण है जो पहले से ही सूची में नहीं हो सकता है।

अभिव्यक्ति

Subject("A") in subject_set 

इसके विपरीत Subject.__hash__() सही बाल्टी मिल जाए, और Subject.__eq__() उपयोग करने के लिए पहली बार इस के बाद ही प्रयोग करेंगे। यदि आपने Subject.__eq__() के साथ संगत तरीके से Subject.__hash__() को परिभाषित नहीं किया है, तो यह असफल हो जाएगा।

+0

धन्यवाद! विषय वर्ग में __hash __() फ़ंक्शन को कार्यान्वित करने से इस समस्या को हल किया गया। – rtclay

2

इन सेट का उपयोग करने के लिए, आपको यह सुनिश्चित करना होगा कि Subject ठीक से हैशबल है। यदि आप __hash__ स्वयं को परिभाषित नहीं करते हैं, तो यह केवल id ले जाएगा, और यह अलग-अलग उदाहरणों के लिए अलग है। __hash__ को परिभाषित किया जाना चाहिए कि समान वस्तुओं के बराबर हैश हो।

3

या तो आपके Subject कक्षा में __hash__() विधि नहीं है, या यह डोडी है। इस प्रयास करें:

def __hash__(self): 
    return hash(self.name) 

डॉक्स here हैं।

4

एक सेट में सदस्यता ऑब्जेक्ट के हैश पर भी निर्भर करती है, और इस तरह आपको कक्षा में उचित रूप से __hash__() विधि को लागू करना होगा।