वस्तुओं के बीच कोई अंतर नहीं है; आप HashMap<String, Object>
दोनों मामलों में एक है। आपके पास ऑब्जेक्ट के लिए इंटरफ़ेस में अंतर है । पहले मामले में, इंटरफ़ेस है HashMap<String, Object>
, जबकि दूसरे में Map<String, Object>
। लेकिन अंतर्निहित वस्तु समान है।
उपयोग करने का लाभ यह Map<String, Object>
है कि आप किसी भी कोड के साथ अपने अनुबंध को तोड़ने के बिना अंतर्निहित वस्तु को एक अलग तरह का नक्शा बदल सकते हैं। यदि आप इसे घोषित करते हैं HashMap<String, Object>
, तो आपको अपना अनुबंध बदलना होगा यदि आप अंतर्निहित कार्यान्वयन को बदलना चाहते हैं।
उदाहरण: मान लीजिए कि मैं यह वर्ग लिखता हूँ:
class Foo {
private HashMap<String, Object> things;
private HashMap<String, Object> moreThings;
protected HashMap<String, Object> getThings() {
return this.things;
}
protected HashMap<String, Object> getMoreThings() {
return this.moreThings;
}
public Foo() {
this.things = new HashMap<String, Object>();
this.moreThings = new HashMap<String, Object>();
}
// ...more...
}
कक्षा में स्ट्रिंग के आंतरिक मानचित्र के कुछ जोड़े हैं-> ऑब्जेक्ट जो इसे उप-वर्ग के साथ साझा करता है (एक्सेसर विधियों के माध्यम से)। मान लें कि मैं इसे HashMap
एस के साथ शुरू करने के लिए लिखता हूं क्योंकि मुझे लगता है कि कक्षा लिखते समय उपयोग करने के लिए उपयुक्त संरचना है।
बाद में, मैरी ने इसे उप-वर्गित करते हुए कोड लिखा। उसके पास कुछ ऐसा है जो उसे दोनों के साथ करने की आवश्यकता है , things
और moreThings
स्वाभाविक रूप से वह उसे एक सामान्य विधि में रखती है, और वह उसी प्रकार का उपयोग करती है जिसका मैंने उपयोग किया getThings
/ getMoreThings
जब उसकी विधि को परिभाषित किया:
class SpecialFoo extends Foo {
private void doSomething(HashMap<String, Object> t) {
// ...
}
public void whatever() {
this.doSomething(this.getThings());
this.doSomething(this.getMoreThings());
}
// ...more...
}
बाद में, मैंने तय करते हैं कि वास्तव में, यह बेहतर होगा यदि मैं का उपयोग TreeMap
करने के बजाय HashMap
में Foo
। मैं अद्यतन Foo
, बदल रहा है HashMap
करने के लिए TreeMap
। अब, SpecialFoo
कोई संकलन नहीं करता है, क्योंकि मैंने अनुबंध को तोड़ दिया है: Foo
यह कहने के लिए उपयोग किया गया है कि यह प्रदान किया गया है HashMap
, लेकिन अब यह TreeMaps
इसके बजाय प्रदान कर रहा है। तो हमें SpecialFoo
अब ठीक करना होगा (और इस तरह की चीज़ कोडबेस के माध्यम से रिपल हो सकती है)।
जब तक कि मेरे पास साझा करने के लिए वास्तव में एक अच्छा कारण नहीं था कि मेरा कार्यान्वयन एक HashMap
(और ऐसा होता है) का उपयोग कर रहा था, मुझे जो करना चाहिए था वह घोषित किया गया था getThings
और getMoreThings
जैसा Map<String, Object>
कि किसी भी विशिष्ट से अधिक विशिष्ट होने के बिना लौट रहा था। वास्तव में, कुछ और करने के लिए एक अच्छा कारण को छोड़कर, यहां तक कि Foo
शायद मुझे घोषित करना चाहिए things
और moreThings
जैसा कि Map
, नहीं HashMap
/ TreeMap
:
class Foo {
private Map<String, Object> things; // <== Changed
private Map<String, Object> moreThings; // <== Changed
protected Map<String, Object> getThings() { // <== Changed
return this.things;
}
protected Map<String, Object> getMoreThings() { // <== Changed
return this.moreThings;
}
public Foo() {
this.things = new HashMap<String, Object>();
this.moreThings = new HashMap<String, Object>();
}
// ...more...
}
ध्यान दें कि मैं अब Map<String, Object>
हर जगह का उपयोग कैसे कर सकता हूं, केवल विशिष्ट होने के नाते जब मैं वास्तविक वस्तुओं का निर्माण करता हूं।
अगर मैंने ऐसा किया होता, तो मैरी ने ऐसा किया होता:
class SpecialFoo extends Foo {
private void doSomething(Map<String, Object> t) { // <== Changed
// ...
}
public void whatever() {
this.doSomething(this.getThings());
this.doSomething(this.getMoreThings());
}
}
... और बदलने Foo
से SpecialFoo
स्टॉप संकलन नहीं हो जाता ।
इंटरफेस (और बेस क्लास) हमें केवल आवश्यकतानुसार परिवर्तन करने के लिए कवर के तहत हमारे लचीलेपन को बनाए रखते हुए, जितना आवश्यक हो उतना ही प्रकट करते हैं । सामान्य तौर पर, हम चाहते हैं कि हमारे संदर्भ यथासंभव बुनियादी हों। अगर हमें यह जानने की आवश्यकता नहीं है कि यह एक है HashMap
, तो इसे कॉल करें a Map
।
यह एक अंधा नियम नहीं है, लेकिन सामान्य तौर पर, सबसे सामान्य इंटरफ़ेस के लिए कोडिंग कुछ अधिक विशिष्ट कोडिंग की तुलना में कम भंगुर होने वाली है। अगर मुझे याद है कि, मैंने Foo
असफलता के लिए मैरी को सेट नहीं किया है SpecialFoo
। अगर मैरी को वह याद था, तो फिर भी मैंने गड़बड़ की Foo
, तो उसने अपनी निजी पद्धति को Map
इसके बजाय घोषित कर दिया होगा HashMap
और मेरे बदलते Foo
अनुबंध ने उसके कोड को प्रभावित नहीं किया होगा।
कभी-कभी आप ऐसा नहीं कर सकते, कभी-कभी आपको विशिष्ट होना पड़ता है। लेकिन जब तक आपके पास कोई कारण न हो, कम से कम विशिष्ट इंटरफ़ेस की ओर।