2009-08-19 9 views
9

गैर-जेनेरिक वर्ग के लिए सामान्य कन्स्ट्रक्टर होने का क्या फायदा है?जेनेरिक कन्स्ट्रक्टर्स का लाभ

class NonGeneric { 
    <T> NonGeneric() { } 
    ... 
    NonGeneric ref = new <String> NonGeneric(); 
} 

एक जब यह वर्ग के typesafety को बढ़ाता है के एक यथार्थवादी उदाहरण के साथ आ सकता है: जावा कल्पना निम्नलिखित परमिट? पहली जगह जेनेरिक का उपयोग करने से बेहतर कैसे होगा।

मैं समझता हूं कि जावा डिजाइनर चाहते थे कि रचनाकार विधियों के साथ अधिक संगत हों। को देखते हुए कंस्ट्रक्टर्स दुष्प्रभाव हो सकता है, सामान्य कंस्ट्रक्टर्स जेनरिक का उपयोग कर सकते कुछ मानकों जिसका संदर्भ बने नहीं रहते हैं, उत्परिवर्तित को

<T> NonGeneric(T obj, List<T> list) { 
    list.add(obj); 
    // Don't hold a reference to list 
} 

उत्तर

4

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

उदाहरण के लिए:

<T> NonGeneric(T[] blank, List<T> list) { 
    // Sort that list 
    T[] array = list.toArray(blank); 
    Arrays.sort(array); 

    // Pull out the values as strings 
    this.list = new ArrayList<String>(array.length); 
    for (T value : array) { 
     this.list.add(value.toString()); 
    } 
} 

यह सबसे अधिक संभावना है सिर्फ कुछ है कि भाषा डिजाइनरों सिर्फ में मामला किसी, यह चाहते थे, क्योंकि वहाँ यह करने से लोगों को रोकने के लिए कोई कारण नहीं था क्या करने का फैसला किया।

+0

हाँ, यह रचनाकारों द्वारा सामान्य तरीकों को प्रतिस्थापित करने की अनुमति देता है (लेकिन आप क्यों चाहेंगे?)। मैंने कभी जंगली में कभी नहीं देखा है। मेरे पैसे के लिए, यह एक जटिलता है कि भाषा बिना हो सकती थी (जैसा सी # ने बाद में जावा जेनरिक के संस्करण को पेश किया था)। –

0

हाँ मैं वही कुछ समय के बारे में सोच रहा था।

हाइपोटेटिकली (एक्सएक्स कारण हैं कि यह ऐसा क्यों नहीं है) यह अच्छा होगा अगर जेनेरिक कन्स्ट्रक्टर पूरे वर्ग के लिए औपचारिक जेनेरिक प्रकार को परिभाषित कर सकें (सामान्य वर्ग घोषणा के रूप में) ... ऐसा कहने के लिए, अगर परिभाषित किया जाता है जेनेरिक निर्माता दिया जाएगा आपको लगता है कि कक्षा में सामान्य क्षेत्रों है ...

उदाहरण के लिए यदि आप सामान्यीकरण से बचना चाहता था:

EntityRequestCallback extends RequestCallback 

लेकिन आप RequestCallback सामान्य RequestCallback<E extends Entity>, आप ऐसा नहीं कर सका बनना चाहता था क्योंकि केवल दो प्रकार के अनुरोध PUT/POST उपयोग इकाई। PUT/POST अनुरोधों के लिए केवल रचनाकारों में इकाई पैरामीटर होता है।

public class RequestCallback { 

     /** GET/DELETE requests */ 
    public RequestCallback(String gttUrl, HttpMethod method,) { 
     this.gttUrl = gttUrl; 
       this.method = method; 
    } 

     /** PUT/POST requests */ 
    public RequestCallback(String gttUrl, HttpMethod method, Entity entity) { 
     this.gttUrl = gttUrl; 
       this.method = method; 
     this.entity = entity; 
    } 
} 

लेकिन वर्ग सामान्य क्योंकि आप एक अनुरोध है कि एक इकाई है, जो मतलब होगा आप का दृष्टांत हैं

new RequestCallback(); //without specifying generic parameter - worse than nothing 

नहीं है के लिए RequestCallback बनाने की जाएगी नहीं किया जा सकता तो यह है कि केवल संभव तरीके से यहाँ है सामान्यीकरण:

EntityRequestCallback<E extends Entry> extends RequestCallback 

तो तुम हो सकता है कि जेनेरिक क्षेत्रों:

public E entity; 

इस विशेष उदाहरण में, सामान्यीकरण वैसे भी सही विकल्प है, लेकिन ऐसे मामले हैं जहां सामान्यीकरण नहीं होगा।

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