2012-07-10 9 views
7

क्योंकि मेरा (यूनिट-) परीक्षण कवरेज अभी भी काफी कम है, दुर्भाग्यवश, मुझे बहुत सारी त्रुटियों को कठिन तरीके से ढूंढना है। इसलिए, रिफैक्टरिंग के दौरान, मैं सी # कंपाइलर की प्रकार की जांच पर भरोसा करता हूं।टाइप-सेफ इक्विल्स()

आज, मैंने x.Equals(aThingWrappingOriginalThing) के साथ एक लाइन खोकर रिफैक्टरिंग के दौरान पेश की गई एक बग तय की। चूंकि यह bool Equals(object T) है, इसलिए संकलक शिकायत नहीं करता था। हालांकि, 9 0% मैं Equals() सीधे (बीसीएल के माध्यम से) का उपयोग करता हूं, मैं तर्कसंगत रूप से उसी प्रकार की वस्तुओं की तुलना करना चाहता हूं।

अब मुझे आश्चर्य है कि मैंने कभी ऐसी स्थितिओं (सी # में) के लिए Equals() के प्रकार-सुरक्षित संस्करण को बढ़ावा देने वाले किसी को क्यों नहीं देखा है। क्या इसके लिए कोई अच्छा अभ्यास है?

public static bool SafeEquals<T>(this T a, T b) 
{ 
    if (a == null) return b == null; 
    return a.Equals(b); 
} 
public static bool SafeEquals<X>(this IEquatable<X> a, IEquatable<X> b) 
{ 
    if (a == null) return b == null; 
    return a.Equals(b); 
} 

इन अनुकूलित किया जा सका:

मैं बहुत की तरह, उन comparisions के लिए एक विस्तार विधि का उपयोग करने के लिए परीक्षा रहा हूँ? http://rickyclarkson.blogspot.com/2006/12/making-equalsobject-type-safe.html

+0

यहां विषय पर कुछ पृष्ठभूमि है: http://blogs.msdn.com/b/ericlippert/archive/2009/04/09/double-your-dispatch-double-your-fun.aspx – Vlad

उत्तर

5

आप के लिए

EqualityComparer<T>.Default.Equals(x,y); 

लिए देख रहे हैं इस IEquatable<T> (यदि लागू किया), और संभवतः-मुक्केबाजी Equals(object) का उपयोग करता है समर्थन करता है; यह कक्षाओं और structs का समर्थन करता है, दोनों के लिए अपेक्षित शून्य व्यवहार के साथ, Nullable<T> (मुक्केबाजी के बिना) के समर्थन सहित।

+0

धन्यवाद, बहुत अच्छा लगता है। क्या यह इसे एक्सटेंशन विधि में लपेटने के लिए प्रदर्शन को नुकसान पहुंचाता है? क्या यह रेखांकित किया जाएगा? – Equalizer

+0

@ एक्वाइलाइज़र एक्सटेंशन विधियां स्थैतिक-कॉल हैं, इसलिए: वास्तव में नहीं, नहीं। यह इच्छुक होने की संभावना नहीं है क्योंकि डीफॉल्ट उपयोग की जाने वाली रणनीति के आधार पर कई ठोस कार्यान्वयन का एक उदाहरण है। निर्णय/प्रतिबिंब केवल टी प्रति बार किया जाता है, इसलिए यह कैश किया जाता है - लेकिन इनलाइन नहीं है। –

2

क्या मैं देख रहा हूँ मेरे लिए अच्छा लग रहा है:

यहाँ विषय मैंने पाया, जावा के लिए के बारे में केवल ब्लॉग पोस्ट है।

मेरे 2 सेंट: मुझे लगता है यह शून्य चेकों को छोड़, और उपयोग करने के लिए इस सरल होगा:

public static bool SafeEquals<T>(this T a, T b) 
{ 
    return object.Equals(a, b); 
} 

बहुत कुछ मामलों में कि अभिप्रेत व्यवहार से विचलित होगा रहे हैं। उनमें से एक है जब Equals झूठी वापसी करता है जब दोनों वस्तुएं एक ही वस्तु होती हैं (जो वैसे भी कभी नहीं होनी चाहिए)।

संदर्भ के लिए, यहां object.Equals डिकंपील्ड किया गया है, ताकि आप स्वयं के लिए क्या देख सकें।

public static bool Equals(object objA, object objB) 
{ 
    return ((objA == objB) || (((objA != null) && (objB != null)) && objA.Equals(objB))); 
} 
+0

'ऑब्जेक्ट। बराबर 'जांच करता है अगर वे दोनों ढेर पर एक ही डेटा को इंगित करते हैं, न कि वे समान हैं। –

+0

@ केंडल यहां पहला कार्यान्वयन ऑब्जेक्ट के चारों ओर सिर्फ एक रैपर है। इसके लिए, इसके लिए, उपभोक्ता को ऑब्जेक्ट कॉल करने की अनुमति क्यों न दें। सभी के लिए यह – Jason

+0

@ColeJohnson के लायक है। लेकिन 'बराबर' और 'संदर्भ एक्वाल्स' –