2009-12-02 13 views
12

मेरे पास एक विधि है, जिसमें अंदर/कोशिश/समापन ब्लॉक है। कोशिश ब्लॉक के भीतर, मैं SqlDataReader की घोषणा इस प्रकार है:कॉलिंग निपटान() बनाम जब कोई वस्तु गुंजाइश हो जाती है/विधि समाप्त होती है

   SqlDataReader aReader = null;   
       aReader = aCommand.ExecuteReader(); 

अंत में ब्लॉक में, वस्तुओं जो मैन्युअल का निपटारा कर रहे हैं उन लोगों के जो श्रेणी स्तर पर स्थापित कर रहे हैं कर रहे हैं। तो उपरोक्त SqlDataReader जैसे IDISposable लागू करने वाली विधि में ऑब्जेक्ट्स, क्या वे स्वचालित रूप से निपटान हो जाते हैं? पाठक की सामग्री प्राप्त करने के लिए थोड़ी देर बाद लूप निष्पादित करने के बाद एक रीडर पर बंद() को कॉल किया जाता है (जिसे निपटाना() होना चाहिए क्योंकि कॉल बंद करें())। अगर बंद() को कोई कॉल नहीं है, तो क्या विधि समाप्त हो जाती है या ऑब्जेक्ट गुंजाइश से बाहर हो जाता है, तो क्या यह ऑब्जेक्ट स्वचालित रूप से बंद/डिस्पोजेड हो जाएगा?

संपादित करें: मुझे उपयोग() कथन का पता है लेकिन ऐसे परिदृश्य हैं जो मुझे भ्रमित कर रहे हैं। Dispose() विधि (जो SqlDataReader के लिए Close() विधि के लिए रवाना से गुजरता है) जब ब्लॉक समाप्त होता है का उपयोग कर बुलाया जाएगा - धन्यवाद

धन्यवाद

उत्तर

24

नहीं, जब वे दायरे से बाहर निकलते हैं तो वस्तुओं को स्वचालित रूप से निपटाया नहीं जाता है।

वे कचरा इकट्ठा होने पर डिस्पोजेड होने की गारंटी भी नहीं देते हैं, हालांकि कई IDisposable ऑब्जेक्ट्स "फॉलबैक" फाइनलजर लागू करते हैं ताकि यह सुनिश्चित किया जा सके कि वे अंततः निपटाए गए हैं।

आप यह सुनिश्चित करने के लिए उत्तरदायी हैं कि IDisposable ऑब्जेक्ट्स का निपटारा किया जाता है, अधिमानतः उन्हें using ब्लॉक में लपेटकर।

8

आप में अपने IDisposable वस्तुओं रैप करने के लिए एक using {...} ब्लॉक का उपयोग करना चाहिए। आप using का उपयोग नहीं करते हैं, तो वस्तु स्वचालित रूप से नहीं निपटारा किया जाएगा जब यह दायरे से बाहर चला जाता है - अगर यह एक है, संसाधनों से छुटकारा पाने के लिए जब यह कचरा एकत्र किया जाता है यह, वस्तु finalizer ऊपर निर्भर करेगा

using (SqlDataReader aReader = aCommand.ExecuteReader()) 
{ 
    // ... do stuff 
} // aReader.Dispose() called here 
1

निपटान पैटर्न इस बात की कोई गारंटी नहीं देता है कि कौन सी वस्तुएं कॉल करेंगी अन्य वस्तुओं पर निपटान करें; यह कभी-कभी हो सकता है, लेकिन आपको परवाह नहीं करनी चाहिए। इसके बजाए, यह सुनिश्चित करना आपकी ज़िम्मेदारी है कि सभी आईडीस्पोजेबल ऑब्जेक्ट्स के लिए निपटान() को बुलाया जाए। ऐसा करने का सबसे अच्छा तरीका using कथन के साथ है। उदाहरण के लिए:

using (SqlDataReader aReader = aCommand.ExecuteReader()) 
{ 
    // your code 
} 
0

मैं कथन से परेशान हूं "अंत में ब्लॉक में, जिन वस्तुओं को मैन्युअल रूप से निपटाया जाता है वे वे हैं जो वर्ग स्तर पर सेट हैं।" वर्ग स्तर पर सेट वस्तुओं द्वारा, क्या आप फ़ील्ड का मतलब है? आपको शायद इन्हें सामान्य विधि के भीतर निपटाना नहीं चाहिए, क्योंकि तब खेतों का जीवनकाल अप्रत्याशित है, और इस बात पर निर्भर करता है कि आपने किन तरीकों को बुलाया था। अपने निपटान विधि में फ़ील्ड के प्रयोज्य और निपटान को लागू करना बेहतर होगा।

1

मैं उपरोक्त सभी के साथ सहमत हूं। आपको यह सुनिश्चित करना चाहिए कि आप Dispose() स्वयं को कॉल करें, और इसका सबसे आसान तरीका using कथन के साथ है (आप इसे finally ब्लॉक में भी कर सकते हैं - यह अधिक वर्बोज़ है, लेकिन कभी-कभी आवश्यक है)। यदि आप ऐसा नहीं करते हैं तो आप अपने एप्लिकेशन को हैंडल, या यहां तक ​​कि अप्रबंधित स्मृति जैसे अप्रबंधित संसाधनों को लीक कर सकते हैं, खासकर यदि इन सभी के नीचे कहीं भी कुछ COM घटकों का उपयोग किया जा रहा है, या Win32 API में कॉल किए जा रहे हैं।यह स्पष्ट रूप से प्रदर्शन और स्थिरता समस्याओं, साथ ही अत्यधिक संसाधन उपयोग के लिए नेतृत्व कर सकते हैं।

सिर्फ इसलिए कि वस्तुओं कि लागू IDisposable एक finaliser कि अप्रबंधित संसाधनों को मुक्त करने के उनके Dispose(bool disposing) प्रणाली को बुलाती लागू "चाहिए", कोई गारंटी नहीं कि यह क्या होगा है, तो आप निश्चित रूप से इस पर निर्भर नहीं होना चाहिए। इस बिंदु पर अधिक जानकारी के लिए, उदाहरण के लिए, http://msdn.microsoft.com/en-us/library/b1yfkh5e%28VS.71%29.aspx देखें।

इसके अलावा, कुछ और ध्यान में रखना, यह है कि यदि आपके प्रकार में ऐसे सदस्य हैं जो डिस्पोजेबल हैं, तो आपके प्रकार को या तो IDisposable लागू करना चाहिए (जब तक उन सदस्यों का जीवन चक्र किसी अन्य प्रकार से प्रबंधित नहीं होता है, जो स्पष्ट रूप से गन्दा हो सकता है) या, यदि आप केवल एक ही विधि में ऐसे सदस्यों का उपयोग करते हैं, या कार्यक्षमता के एक विशेष टुकड़े को लागू करने के लिए, आपको उन तरीकों से स्थानीय चर/पैरामीटर बनाने पर विचार करना चाहिए।

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

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