2012-01-23 16 views
16

मैं here कि एक विधि वापसी प्रकार में एक घिरे वाइल्डकार्ड होने एक बुरा विचार है सहित कई स्थानों में पढ़ा है। हालांकि, मुझे अपनी कक्षा से बचने का कोई रास्ता नहीं मिल रहा है। क्या मैं कुछ भूल रहा हूँ? करने के लिए किसी भी प्रकाशन अंग्रेजी के लिए किसी भिन्न रूप में है कि उपभोगजावा वापसी प्रकार में घिरे वाइल्डकार्ड

class EnglishReaderOfPublications { 

    private final Publication<? extends English> publication; 

    EnglishReaderOfPublications(Publication<? extends English> publication) { 
     this.publication = publication; 
    } 

    void readPublication() { 
     publication.omNomNom(); 
    } 

    Publication<? extends English> getPublication() { 
     return publication; 
    } 
} 

सारांश में, एक वर्ग है कि मैं सक्षम होना चाहते हैं:

स्थिति कुछ इस तरह लग रहा है। कक्षा को प्रकाशन से बाहर पहुंच की अनुमति देने की आवश्यकता है, लेकिन आदर्श रूप से, getPublication के कॉलर परिणाम को बाध्य वाइल्डकार्ड के रूप में नहीं चाहते हैं। वे Publication<English> से खुश होंगे।

क्या इस दौर में कोई रास्ता है?

+0

आइटम यहोशू बलोच की "प्रभावी जावा" में 28 की सिफारिश की: "वापसी प्रकार के रूप में वाइल्डकार्ड प्रकार का प्रयोग न करें।" –

उत्तर

12

घिरा वाइल्डकार्ड संक्रामक हैं, जो कि आप कौन सा पेज से लिंक विलाप करने के लिए लगता है। खैर, कोई इनकार नहीं कर रहा है ... लेकिन मुझे लगता है कि मैं इसे इतनी बड़ी समस्या के रूप में नहीं देखता हूं।

ऐसे कई मामले हैं जहां मैं एक बाध्य वाइल्डकार्ड बिल्कुल लौटाता हूं क्योंकि यह संक्रामक है। बेहतर या बदतर के लिए जेडीके (मैं बदतर के लिए कहता हूं, लेकिन यह एक अलग साबुन बॉक्स है :)) में केवल पढ़ने के संग्रह के लिए इंटरफेस नहीं हैं। अगर मैं List<Foo> लौटाता हूं कि मैं नहीं चाहता कि लोग संशोधित करें (शायद यह Collections.unmodifiableList में भी सुरक्षित रूप से लपेटा गया है), मेरे रिटर्न हस्ताक्षर में घोषणा करने का कोई तरीका नहीं है। एक गरीब व्यक्ति के कामकाज के रूप में, मैं अक्सर List<? extends Foo> वापस आऊंगा। यह अभी भी तत्वों को हटाने या null डालने से उस सूची को संशोधित करने की कोशिश करने के लिए संभव है, लेकिन कम से कम तथ्य यह है कि आप add(new Foo()) आपको याद दिला दें कि इस सूची शायद है केवल पढ़ने के लिए का एक सा के रूप में नहीं कार्य करता है सकते हैं।

आम तौर पर, मुझे लगता है कि एक घिरे वापसी प्रकार के साथ कुछ लौटने पूरी तरह से उचित है क्या तुम सच में चाहते हैं, तो कॉल साइट वस्तु सीमित एक्सेस है करने के लिए।

एक अन्य उदाहरण एक धागा सुरक्षित कतार है कि आप अलग अलग धागे, जहां एक धागा एक उत्पादक देश है और अन्य एक उपभोक्ता है के लिए रवाना हाथ होगा। यदि आप निर्माता को Queue<? super Foo> देते हैं, तो यह स्पष्ट है कि आप उन्हें इसमें आइटम डालने का इरादा रखते हैं (और आइटम नहीं लेते)। इसी प्रकार, यदि आप उपभोक्ता को Queue<? extends Foo> देते हैं, तो यह स्पष्ट है कि आप उन्हें आइटम ले जाने का इरादा रखते हैं (और आइटम नहीं डालते)।

4

क्या आप कक्षा घोषणा में बाध्य प्रकार पैरामीटर का उपयोग कर सकते हैं?

class EnglishReaderOfPublications<E extends English> { ... 

फिर आप इस प्रकार पैरामीटर का उपयोग कर सकते हैं जहां आपके पास वाइल्डकार्ड पैरामीटर है।

+1

मैं कर सकता था लेकिन मुझे यकीन नहीं है कि यह मेरे मामले में मदद करता है।मेरे पास इन अंग्रेजी पाठकों का एक विषम संग्रह है और मैं उनसे प्रकाशन प्राप्त करना चाहता हूं जब मेरी परवाह है कि वे 'प्रकाशन ' हैं। मुझे लगता है कि मेरा प्रश्न इस बारे में अधिक है कि 'प्रकाशन ' 'प्रकाशन <जैसा नहीं है? अंग्रेजी बढ़ाता है ''। मुझे लगता है कि यह संग्रह के लिए क्यों है (आप वाइल्डकार्ड से संतुष्ट कुछ जोड़ सकते हैं लेकिन वास्तविक प्रकार का उल्लंघन किया है), लेकिन प्रकाशन के रूप में प्रकाशन को भाषा बदलने के लिए कोई रास्ता नहीं प्रदान करता है, मैं वास्तव में महसूस नहीं कर रहा हूं * यह क्यों होगा गलत। प्रदूषण की वजह से – thehouse

0

"आदर्श रूप से, GetPublication के कॉलर्स परिणाम को बाध्य वाइल्डकार्ड के रूप में नहीं चाहते हैं। वे Publication<English> से खुश होंगे।"

क्यों "वे" नहीं चाहते हैं? क्या वे Publication<? extends English> के साथ "खुश रहेंगे"? सवाल यह है कि इन कॉलर्स को इस प्रकाशन ऑब्जेक्ट के साथ क्या करने की ज़रूरत है। यदि वे सब कुछ करते हैं तो इससे चीजें मिलती हैं, फिर Publication<? extends English> पर्याप्त है, और यह बेहतर है क्योंकि यह अधिक सामान्य है। हालांकि, अगर उन्हें चीजों को इसमें डालना है, तो आप Publication<? extends English> का उपयोग नहीं कर सकते हैं।

+0

मूल रूप से। कॉलिंग कोड प्रत्येक प्रकाशन को 'getPublication' को कॉल करके प्राप्त करता है और इसे' सेट 'में रखता है। फिलहाल मुझे 'सेट <प्रकाशन <' पास करना होगा? अंग्रेजी बढ़ाता है >> 'जो मेरे कोड को पढ़ने के लिए कड़ी मेहनत कर रहा है। शायद मैं उग्र हो रहा हूँ। – thehouse

+0

पढ़ने के लिए कठिन, लेकिन उपयोग करने के लिए अधिक सामान्य। मैं मानता हूं कि वाक्यविन्यास दुर्भाग्य से वर्बोज़ है। यदि ये कक्षाएं/विधियां केवल आपके कोड में हैं, तो आप इसे बेहतर तरीके से पढ़ने के लिए आसानी से पढ़ने के दृष्टिकोण के लिए जा सकते हैं। यदि आप एक एपीआई लिख रहे हैं जिसे आप दूसरों को पढ़ने की उम्मीद करते हैं, तो वाइल्डकार्ड को सही तरीके से प्राप्त करना बहुत महत्वपूर्ण है - क्योंकि किसी के पास प्रकाशन होने पर शर्म की बात होगी और "आलसी" (या "सुंदर", अगर आपको पसंद है) की वजह से इसे अपने एपीआई में उपयोग नहीं कर सका। – yshavit

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