2011-08-09 13 views
6

मैं व्यस्त रिश्तों के साथ दो इंटरफेस बनाना चाहता हूं।व्यस्त रिश्तों के साथ जेनेरिक इंटरफेस

public interface Item <D extends Description, 
             C extends Category<D,Item<D,C>>> { 
    public C getCategory(); 
    public void setCategory(C category);} 

मुझे यकीन है कि अगर अभिव्यक्ति C extends Category<D,Item<D,C>> सही है, लेकिन कम से कम वहाँ कोई संकलक त्रुटियाँ हैं नहीं कर रहा हूँ।

public interface Category<D extends Description, I extends Item> { 
    public List<I> getItems(); 
    public void setItems(List<I> items);} 

I extends Item चेतावनी Item is a raw type. References to Item<D,C> should be parametrized देता है। मैंने

I extends Item<D,Category<D,I>> 

पर यह परिणाम Bound mismatch: The type Category<D,I> is not a valid substitute for the bounded parameter <C extends Category<D,Item<D,C>>> of the type Item<D,C> त्रुटि में परिणाम दिया। मैं जेनेरिक के साथ इंटरफेस Category सही ढंग से कैसे parametrize?

उत्तर

2

यह काम करने लगता है :)।

interface Description {} 

interface Item<D extends Description, I extends Item<D, I, C>, C extends Category<D, C, I>> 
{ 
    public C getCategory(); 
    public void setCategory(C category); 

} 

interface Category<D extends Description, C extends Category<D, C, I>, I extends Item<D, I, C>> {  
    public List<I> getItems(); 
    public void setItems(List<I> items); 
} 

class DescriptionImpl implements Description {} 

class CustomItem implements Item<DescriptionImpl, CustomItem, CustomCategory> { 
    public CustomCategory getCategory() { 
     return null; 
    } 

    public void setCategory(CustomCategory category) { 
    } 
} 

class CustomCategory implements Category<DescriptionImpl, CustomCategory, CustomItem> { 

    public List<CustomItem> getItems() { 
     return null;   } 

    public void setItems(List<CustomItem> items) { 
    } 
} 

अब अगर आप ऐसा करते हैं:

CustomCategory customCategory = new CustomCategory(); 
CustomItem customItem = new CustomItem(); 
DescriptionImpl description = new DescriptionImpl(); 

customItem.getCategory(); 

श्रेणी के प्रकार लौटे मैं पता नहीं यह (मैं सामान्य रूप से ऐसा कोई काम कर से बचने की कोशिश), लेकिन यहाँ यह जाता है कि कैसे समझाने के लिए है customItem.getCategory() द्वारा कस्टम श्रेणी है जो मुझे लगता है कि आप वास्तव में क्या चाहते हैं।

+0

अजीब लग रहा है लेकिन काम लगता है! – Thor

+0

हाँ :) यह मेरे लिए और अधिक अजीब है क्योंकि मैं वास्तव में इसे समझा नहीं सकता :)) –

0

इस चेतावनी के बिना संकलित:

interface Description {} 

interface Item<D extends Description, C extends Category<D, Item<D, C>>> { 
    public C getCategory(); 
    public void setCategory(C category); 
} 

public interface Category<D extends Description, I extends Item<D, ?>> { 
    public List<I> getItems(); 
    public void setItems(List<I> items); 
} 

मैं I extends Item<D, ?> बनाया है। यद्यपि इसमें कोई चेतावनी नहीं है, इससे आपको अन्य समस्याएं हो सकती हैं - मुझे बताएं कि यह क्या करता है और मैं देखता हूं कि मैं क्या कर सकता हूं।

+0

चूंकि मुझे पता है कि मेरे पास किस प्रकार की वस्तु है, मुझे नहीं लगता कि मैं 'का उपयोग करना चाहता हूं। – Thor

0

की पहली पर विवरण के बारे में भूल करते हैं और सिर्फ कुछ अच्छा सममित इंटरफेस बनाने:

interface Item<C extends Category<Item<C>>> {} 

interface Category<I extends Item<Category<I>>> {} 

विवरण के लिए, आप के लिए दो अलग-अलग विवरण प्रकार चाहते हो सकता है वस्तु और श्रेणी।

अधिक सामान्य नोट पर, मुझे यकीन नहीं है कि आपका डिज़ाइन एक अच्छा विचार है। मुझे नहीं पता कि आप इसके लिए क्या उपयोग करेंगे, लेकिन ऐसा कुछ ऐसा लगता है जो सही तरीके से उपयोग करना मुश्किल होगा।

इसके अलावा, item.setCategory(c) के साथ कुछ गलत लगता है क्योंकि item पहले से ही किसी श्रेणी द्वारा parametrized है।

0

, इस सरल समस्या

interface Item<C extends Container<Item<C>>> 

interface Container<I extends Item<Container<I>>> 

यह काम नहीं करता है पर विचार करें क्योंकि Container<Item<C>> के उपप्रकार काफी सीमित हैं - Container<MyItem> इसके बारे में एक उप प्रकार नहीं है, जैसे List<string>List<Object>

की एक उप प्रकार नहीं है हम इसे वाइल्डकार्ड से आराम कर सकते हैं:

interface Item<C extends Container<? extends Item<C>>> 

interface Container<I extends Item<? extends Container<I>>> 

अब यह ठीक काम करता है

class MyItem implements Item<MyContainer> 

class MyContainer implements Container<MyItem> 

अधिकतर।निम्नलिखित घोषणा भी अनुमति दी है, लेकिन हम क्या नहीं इरादा

class HerItem implements Item<MyContainer> // nooo! 

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

आदर्श रूप में, हम एक This प्रकार चाहेगा, और हमारे इरादा बाधाओं के रूप में

interface Item<C extends Container<This>>> 

interface Container<I extends Item<This>> 

जब से हम This नहीं है, एक एक प्रकार पैरामीटर द्वारा यह दृष्टिकोण करने का प्रयास करेंगे व्यक्त किया जा सकता

interface Item<C extends Container<This, C>>, This extends Item<C, This> > 

interface Container<I extends Item<This, I>, This extends Container<I, This>> 

(या, और अधिक संतुलित

interface Item<C extends Container<I, C>>, I extends Item<C, I> > 

    interface Container<I extends Item<C, I>, C extends Container<I, C>> 

) हालांकि, यह वास्तव में या तो तंग नहीं है। This वास्तव में "इस प्रकार" नहीं है। यह एक बार फिर,

class HerItem implements Item<MyContainer, MyItem> // uh? 

संभव है हम ऐसे ही सामान नहीं करने के लिए प्रोग्रामर के अनुशासन पर भरोसा करना चाहिए।

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