अपनी पहली 'गंभीर' सी ++ लाइब्रेरी डिजाइन करते समय, मैं खुद से पूछ रहा हूं:
क्या यह अच्छी शैली है कि इससे अपवादों को प्राप्त करें std::exceptionऔर यह संतान है ?!
पढ़ने के बाद भी
- अपवाद कक्षाओं को डिजाइन करना
- मेरे पुस्तकालय को लागू करने के लिए अपवादों की एक 'अच्छी संख्या' क्या है?
मुझे अभी भी निश्चय नही है। क्योंकि, सामान्य (लेकिन शायद अच्छा नहीं) अभ्यास के अलावा, मैं एक पुस्तकालय उपयोगकर्ता के रूप में मान सकता हूं, कि एक पुस्तकालय समारोह std::exceptionकेवल तभी फेंक देगा जब मानक पुस्तकालय कार्य पुस्तकालय कार्यान्वयन में विफल हो जाते हैं, और यह इसके बारे में कुछ भी नहीं कर सकता है। लेकिन फिर भी, जब आवेदन कोड लिखना, मेरे लिए यह बहुत सुविधाजनक है, और यह भी IMHO अच्छा सिर्फ एक फेंक करने के लिए देख रहे हैं std::runtime_error। इसके अलावा मेरे उपयोगकर्ता भी परिभाषित न्यूनतम इंटरफ़ेस, जैसे what()या कोड पर भरोसा कर सकते हैं ।
और उदाहरण के लिए, मेरे उपयोगकर्ता दोषपूर्ण तर्कों की आपूर्ति करते हैं, जो एक फेंकने की तुलना में अधिक सुविधाजनक std::invalid_argumentहोगा, यह नहीं होगा? इसलिए std के सामान्य उपयोग के साथ संयुक्त :: अपवाद मैं दूसरों के कोड में देखता हूं: अपने कस्टम अपवाद वर्ग (जैसे lib_foo_exception) से और भी अधिक क्यों न हो std::exception।
विचार?
lib_foo_exceptionसे वर्ग की व्युत्पत्ति std::exception, पुस्तकालय उपयोगकर्ता पकड़ lib_foo_exceptionबस पकड़ने से std::exceptionजब वह केवल पुस्तकालय एक कैच के अलावा,। इसलिए मैं यह भी पूछ सकता था कि क्या मेरे पुस्तकालय को मूल जड़ वर्ग से होना चाहिए :: अपवाद ।
lib_foo_exception?" std::exceptionआप से विरासत में catch(std::exception)या के द्वारा यह कर सकते हैं catch(lib_foo_exception)। से व्युत्पन्न के बिना std::exception, आप इसे पकड़ लेंगे यदि और केवल यदि , द्वारा catch(lib_foo_exception)।
catch(...)। यह इसलिए है क्योंकि भाषा उस मामले के लिए अनुमति देती है जिस पर आप विचार कर रहे हैं (और "दुर्व्यवहार" पुस्तकालयों के लिए), लेकिन यह आधुनिक सर्वोत्तम अभ्यास नहीं है।
catchसाइटों को प्रोत्साहित करता है, और इसी तरह मोटे लेन-देन को भी करता है जो एक उपयोगकर्ता-अंत ऑपरेशन को मॉडल करता है। यदि आप इसकी तुलना उन भाषाओं से करते हैं जो सामान्यीकृत पकड़ने के विचार को बढ़ावा नहीं देते हैं std::exception&, उदाहरण के लिए, उनके पास अक्सर try/catchबहुत विशिष्ट त्रुटियों से संबंधित मध्यस्थ ब्लॉकों के साथ एक बहुत अधिक कोड होता है , जो अपवाद-हैंडलिंग की व्यापकता को कम कर देता है क्योंकि यह शुरू हो रहा है। मैनुअल एरर हैंडलिंग पर अधिक मजबूत जोर, और संभवतः सभी संभावित त्रुटियों पर भी।
std::exceptionहैं इसका मतलब यह नहीं है कि आप एक फेंक देते हैंstd::exception। इसके अलावा, पहली जगहstd::runtime_errorसे विरासत में मिलाstd::exceptionहै, औरwhat()विधि से आता हैstd::exception, नहींstd::runtime_error। और आपको निश्चित रूप से जेनेरिक अपवादों को फेंकने के बजाय अपनी खुद की अपवाद कक्षाएं बनानी चाहिएstd::runtime_error।