2012-05-23 18 views
14

मैं एक अंतरफलक बिगड़ने के रूप में, BaseObjectजावा - गुजर इंटरफ़ेस प्रकार की ArrayList

public class BaseObject implements Damageable 

अब एक तृतीय श्रेणी में

public interface Damageable { 
    public void handleCollision(float impulse); 
} 

एक वर्ग जो इस इंटरफेस को लागू करता है इस प्रकार है, मैं का एक ArrayList है प्रकार बेसऑब्जेक्ट

public class ObjectManager {  
    public ArrayList<BaseObject> bodies; 

जो मैं करने की कोशिश कर रहा हूं वह है कि ऐरेलिस्ट निकायों को दांत की विधि में पारित करना है एर वर्ग जो ArrayList

public CollisionManager(ArrayList<Damageable> _bodies) { 
     bodies = _bodies; 
} 

जावा स्वीकार करता है मुझे नए CollisionManager (शरीर) कर जहां शरीर प्रकार ArrayList के है नहीं करता है और BaseObject बिगड़ने

मैं कास्टिंग की कोशिश की है लागू करता है। कहते हैं कि ArrayList<BaseObject> से ArrayList पर भी Class<? extends Damageable> का उपयोग करने का प्रयास नहीं किया गया है, लेकिन फिर मैं इंटरफ़ेस में घोषित विधियों को कॉल करने में असमर्थ हूं। मैं ऐरेलिस्ट को कैसे पास कर सकता हूं?

+0

की जांच: http://stackoverflow.com/questions/6965035/why-cant-a-method-take-a-collectionsubclass-when-the-methods-signature-is-de – SirPentor

उत्तर

32

आप अपने जेनरिक के साथ स्पष्ट होना जरूरी से मिलकर चाहते हैं। इसलिए, आप संकलक है कि अपने सामान्य प्रकार नहीं होने की है करता है सूचित करने के लिए एक Damagable दर असल, बल्कि यह Damagable विस्तार कर सकते हैं:

public CollisionManager(ArrayList<? extends Damagable> bodies) { 

वैसे, कि मैं नोटिस _bodies के बजाय अपने चर को bodies में बदल दिया। अंडरस्कोर मानक जावा कोडिंग सम्मेलनों का हिस्सा नहीं हैं।

ओपी की टिप्पणी के जवाब में

संपादित

की है कि कहते हैं, एक अंतरफलक के बजाय करते हैं, तो आप एक ठोस वर्ग Damagable कहा जाता था। कंपाइलर को <? extends Damagable> बताते हुए कहते हैं कि इसे Damagable का उदाहरण नहीं होना चाहिए। यह ठीक है कि Damagable का विस्तार करें। अन्यथा, संकलक मानता है कि आपके पास Damagableबिल्कुल है।

जब आप Damagable के बारे में सोचते हैं तो यह अधिक समझ में नहीं आता है, क्योंकि ऐसा कोई मामला नहीं है जहां आपके पास Damagable का उदाहरण होगा। लेकिन वे अनिवार्य रूप से उसी तरह काम करते हैं।

आपको याद रखना होगा कि आप जावा प्रकार, कक्षाओं के साथ काम नहीं कर रहे हैं। जावा के प्रकार सिंटैक्स और संरचना इसकी कक्षा संरचना से कम मजबूत है।जब प्रकारों की बात आती है तो implements की कोई अवधारणा नहीं है।


संपादन के अंतिम दौर

अंत में, मैं नोट करना चाहिए कि यह आम तौर पर विधि/निर्माता मापदंडों और विधि वापसी प्रकार के लिए एक इंटरफेस का उपयोग करना बेहतर है। यह आपको और जो आपके द्वारा उपयोग किए जाने वाले कार्यान्वयन का उपयोग करने के लिए आपके तरीकों का उपयोग करने की अनुमति देता है, और आपको कृपया अपना कार्यान्वयन बदलने की अनुमति देता है।

उन बदलावों के साथ, तो, आप होगा:

public CollisionManager(List<? extends Damagable> bodies) { 
+0

उत्तर के लिए धन्यवाद, लेकिन ArrayList को नुकसान पहुंचाने के लिए है क्योंकि मैं उस इंटरफेस के तरीकों का उपयोग कर रहा हूं। – wirate

+1

'? जावा जेनेरिक-बोल में हानिकारक '* साधन *' दमनीय 'लागू करता है। –

+0

मुझे इसकी पुष्टि करने दें। ArrayList का मतलब किसी भी प्रकार का एक ऐरेलिस्ट है जो इंटरफ़ेस को विस्तारित या कार्यान्वित करता है? – wirate

2

ArrayList<? extends Damageable > _bodies आज़माएं।

यह कहता है कि आप एक ArrayList एक Class कि फैली हुई है (अच्छी तरह से लागू करता) Damageable

+0

क्या है ArrayList <<कक्षा <के बीच का अंतर? क्षतिग्रस्त>> और ArrayList <विस्तारित करता है? नुकसान पहुंचाता है>? – wirate

+0

मैं यहां गलत हो सकता हूं, लेकिन मुझे कुछ भी नहीं लगता है। आपके द्वारा डाला गया एक निर्दिष्ट करता है कि यह एक वर्ग होना चाहिए, और हानिकारक को लागू/कार्यान्वित करना है, लेकिन बेशक इसे एक वर्ग होना चाहिए (फिर भी मुझे लगता है)। हालांकि यह मेरे जेनेरिक ज्ञान की सीमाओं के करीब आ रहा है। क्या आपका संकलन करता है? –

+0

ऐरेलिस्ट <<कक्षा > काम करने योग्य नहीं था क्योंकि ऐसा करने से मुझे इंटरफ़ेस में घोषित विधियों को कॉल करने की अनुमति नहीं दी जाएगी। – wirate

2

दूसरों कोई संदेह नहीं है जावा वाक्य रचना के नजरिए से तकनीकी समाधान का कहना होगा।

  • आपका BaseObject बिगड़ने लागू करता है:

    मैं बस कुछ डिजाइन मुद्दों है कि आप शायद विचार करना चाहिए उल्लेख करने के लिए जा रहा हूँ। इसका मतलब है कि सभी बेस ऑब्जेक्ट्स क्षतिग्रस्त हैं। फिर CollisionManager(ArrayList<BaseObject>) क्यों न करें? जब तक आप कहीं और क्षतिग्रस्त उपयोग करने जा रहे हैं (यानी ऐसी चीजें हैं जो क्षतिग्रस्त हैं लेकिन बेसऑब्जेक्ट्स नहीं हैं) तो यह एक अनावश्यक अमूर्तता की तरह प्रतीत होती है।

  • आम तौर पर किसी गेम/सिमुलेशन में टकराव का पता लगाने के लिए आप एरेलेस्टिस्ट की बजाय टकराव का पता लगाने (जैसे ऑक्ट्री, क्वाड्री या एएबीबी पेड़) के लिए स्थानिक डेटा संरचना का उपयोग करना चाहते हैं। एक ArrayList में टक्कर के लिए खोज एक ओ (एन^2) एल्गोरिदम है। यदि आपके पास बहुत सारी जीव वस्तुएं हैं तो यह एक बड़ा मुद्दा बन जाएगा।
  • क्षतिग्रस्त एक बुरे नाम की तरह प्रतीत होता है, क्योंकि कार्यक्षमता क्षति के बजाय टकराव का पता लगाने से संबंधित है - क्या Collidable बेहतर नहीं होगा? इस पोस्ट के बाहर
+0

विषय से +1 +1 हो सकता है, लेकिन निश्चित रूप से सहायक! –

+0

असल में मैंने 1 बिंदु में जो सुझाव दिया था वह किया। मैं बस सतर्क था। प्वाइंट 2: बॉक्स 2 डी टकराव का पता लगा रहा है और मुझे टकराव का पता चलने पर इस प्रकार एक विधि को कॉल करना होगा प्वाइंट 3: मेरी स्थिति में ऐसी वस्तुएं हैं जो टकराती हैं लेकिन कभी क्षतिग्रस्त नहीं होतीं – wirate