जैसा कि आप स्पष्ट रूप से पहले ही समझ चुके हैं, हां, सी ++ उस तंत्र के बिना समान क्षमताएं प्रदान करता है। जैसे, सख्ती से बोलना, try
/ finally
तंत्र वास्तव में आवश्यक नहीं है।
उस ने कहा, इसके बिना ऐसा करना कुछ आवश्यकताओं को उस तरह से लागू करता है जिस तरह से बाकी भाषा को डिज़ाइन किया गया है। C ++ में क्रियाओं का एक ही सेट एक वर्ग 'विध्वंसक में सन्निहित है। यह मुख्य रूप से (विशेष रूप से?) काम करता है क्योंकि सी ++ में विनाशकारी आह्वान नियतात्मक है। यह बदले में, वस्तु जीवनकाल के बारे में कुछ जटिल नियमों की ओर जाता है, जिनमें से कुछ निश्चित रूप से गैर-सहज हैं।
अधिकांश अन्य भाषाएं इसके बजाय कचरा संग्रहण का कुछ रूप प्रदान करती हैं। हालांकि, कचरा संग्रह के बारे में कुछ चीजें हैं जो विवादास्पद हैं (उदाहरण के लिए, स्मृति प्रबंधन के अन्य तरीकों के सापेक्ष इसकी दक्षता) एक चीज आम तौर पर नहीं होती है: सही समय जब कोई वस्तु कचरा कलेक्टर द्वारा "साफ किया जाएगा" सीधे बंधा नहीं होता है वस्तु का दायरा। यह इसके उपयोग को रोकता है जब सफाई के लिए नियतात्मक होने की आवश्यकता होती है, जब इसे केवल सही संचालन के लिए आवश्यक होता है, या संसाधनों से निपटने के दौरान इतना कीमती होता है कि उनकी सफाई में सबसे ज्यादा देरी न हो। try
/ finally
ऐसी भाषाओं के लिए उन परिस्थितियों से निपटने के लिए एक रास्ता प्रदान करता है जिनके लिए उस निर्धारक सफाई की आवश्यकता होती है।
मुझे लगता है कि यह दावा करने वाले कि इस क्षमता के लिए C ++ सिंटैक्स जावा की तुलना में "कम अनुकूल" है, बल्कि बिंदु को याद नहीं कर रहे हैं। इससे भी बदतर, वे जिम्मेदारी के विभाजन के बारे में बहुत अधिक महत्वपूर्ण बिंदु याद कर रहे हैं जो वाक्यविन्यास से बहुत आगे निकल जाता है, और कोड को कैसे डिज़ाइन किया गया है, इसके बारे में बहुत कुछ किया है।
C ++ में, यह निर्धारक सफाई वस्तु के विनाशकर्ता में होती है। इसका मतलब है कि वस्तु को साफ किया जा सकता है (और आम तौर पर होना चाहिए)। यह ऑब्जेक्ट ओरिएंटेड डिज़ाइन के सार पर जाता है - एक एब्स्ट्रैक्शन प्रदान करने के लिए एक क्लास डिज़ाइन किया जाना चाहिए, और अपने स्वयं के इन्वेंटर्स को लागू करना चाहिए। C ++ में, एक व्यक्ति ठीक यही करता है - और इनवैलेंट में से एक जिसके लिए यह प्रदान करता है कि जब ऑब्जेक्ट नष्ट हो जाता है, तो उस ऑब्जेक्ट द्वारा नियंत्रित संसाधनों (उनमें से सभी, न केवल मेमोरी) को सही तरीके से नष्ट कर दिया जाएगा।
जावा (और समान) कुछ अलग हैं। हालांकि वे (तरह) समर्थन करते हैं finalize
जो सैद्धांतिक रूप से समान क्षमता प्रदान कर सकते हैं, समर्थन इतना कमजोर है कि यह मूल रूप से अनुपयोगी है (और वास्तव में, अनिवार्य रूप से कभी उपयोग नहीं किया गया)।
नतीजतन, वर्ग खुद को आवश्यक सफाई करने में सक्षम होने के बजाय, वर्ग के ग्राहक को ऐसा करने के लिए कदम उठाने की आवश्यकता होती है। यदि हम पर्याप्त रूप से अदूरदर्शी तुलना करते हैं, तो यह पहली नज़र में दिखाई दे सकता है कि यह अंतर काफी मामूली है और जावा इस संबंध में C ++ के साथ काफी प्रतिस्पर्धी है। हम कुछ इस तरह से समाप्त करते हैं। C ++ में, क्लास कुछ इस तरह दिखता है:
class Foo {
// ...
public:
void do_whatever() { if (xyz) throw something; }
~Foo() { /* handle cleanup */ }
};
... और ग्राहक कोड कुछ इस तरह दिखता है:
void f() {
Foo f;
f.do_whatever();
// possibly more code that might throw here
}
जावा में हम एक छोटे से अधिक कोड का आदान-प्रदान करते हैं जहां वस्तु का उपयोग कक्षा में थोड़ा कम किया जाता है। यह शुरू में बहुत सुंदर ट्रेड-ऑफ की तरह दिखता है। वास्तव में, हालांकि यह इससे बहुत दूर है, क्योंकि अधिकांश विशिष्ट कोड में हम केवल एक ही स्थान पर वर्ग को परिभाषित करते हैं , लेकिन हम इसे कई स्थानों पर उपयोग करते हैं। C ++ दृष्टिकोण का अर्थ है कि हम केवल उस कोड को एक स्थान पर सफाई से निपटने के लिए लिखते हैं। जावा दृष्टिकोण का मतलब है कि हमें उस कोड को सफाई को संभालने के लिए कई बार लिखना होगा, कई जगहों पर - हर जगह हम उस वर्ग की एक वस्तु का उपयोग करते हैं।
संक्षेप में, जावा दृष्टिकोण मूल रूप से गारंटी देता है कि हम प्रदान करने की कोशिश करने वाले कई सार "लीक" हैं - किसी भी और हर वर्ग को निर्धारक सफाई की आवश्यकता होती है जो वर्ग के ग्राहक को सफाई और क्या सफाई करने के तरीके के बारे में जानने के लिए बाध्य करता है। , बल्कि उन विवरणों को कक्षा में ही छिपाया जा रहा है।
हालांकि मैं यह "जावा दृष्टिकोण" कहा जाता है की है ऊपर, try
/ finally
और अन्य नामों के तहत एक जैसी कार्यविधि पूरी तरह जावा के लिए सीमित नहीं हैं। एक प्रमुख उदाहरण के लिए, .NET भाषाओं (जैसे, C #) के अधिकांश (सभी?) समान प्रदान करते हैं।
जावा और सी # दोनों के हाल के पुनरावृत्तियों ने इस संबंध में "क्लासिक" जावा और सी ++ के बीच एक आधा बिंदु का कुछ भी प्रदान किया है। C # में, एक ऑब्जेक्ट जो अपने क्लीनअप को स्वचालित करना चाहता है IDisposable
, इंटरफ़ेस को लागू कर सकता है, जो Dispose
कि एक विधि प्रदान करता है जो (C कम से कम अस्पष्ट) C ++ विध्वंसक के समान है। जबकि इसका उपयोग जावा में / जैसे के माध्यम से किया जा सकता है , सी # कार्य को एक बयान के साथ थोड़ा और स्वचालित करता है जो आपको उन संसाधनों को परिभाषित करने देता है जो एक गुंजाइश के रूप में बनाए जाएंगे, और गुंजाइश से बाहर होने पर नष्ट हो जाएंगे। हालाँकि C ++ द्वारा प्रदान किए गए स्वचालन और निश्चितता के स्तर में अभी भी अच्छी तरह से कमी है, यह अभी भी जावा पर पर्याप्त सुधार है। विशेष रूप से, वर्ग डिजाइनर कैसे के विवरण को केंद्रीकृत कर सकता हैtry
finally
using
के कार्यान्वयन में वर्ग के निपटान के लिए IDisposable
। क्लाइंट प्रोग्रामर के लिए जो कुछ भी बचा है, वह यह using
सुनिश्चित करने के लिए एक बयान लिखने का कम बोझ है कि IDisposable
इंटरफ़ेस का उपयोग तब किया जाएगा जब यह होना चाहिए। जावा 7 और नए में, दोषियों को बचाने के लिए नाम बदल दिए गए हैं, लेकिन मूल विचार मूल रूप से समान है।