Ruby Language
अपवाद
खोज…
टिप्पणियों
एक अपवाद एक वस्तु है जो एक असाधारण स्थिति की घटना का प्रतिनिधित्व करता है। दूसरे शब्दों में, यह इंगित करता है कि कुछ गलत हुआ।
रूबी में, अपवादों को अक्सर त्रुटियों के रूप में संदर्भित किया जाता है। ऐसा इसलिए है क्योंकि आधार Exception
वर्ग एक शीर्ष-स्तरीय अपवाद ऑब्जेक्ट तत्व के रूप में मौजूद है, लेकिन उपयोगकर्ता-परिभाषित निष्पादन अपवाद आम तौर पर StandardError
या वंशज हैं।
एक अपवाद उठाना
एक अपवाद का उपयोग करने के लिए Kernel#raise
अपवाद वर्ग और / या संदेश पास करते हुए बढ़ाएँ:
raise StandardError # raises a StandardError.new
raise StandardError, "An error" # raises a StandardError.new("An error")
आप बस एक त्रुटि संदेश भी दे सकते हैं। इस मामले में, संदेश एक में लपेटा जाता है RuntimeError
:
raise "An error" # raises a RuntimeError.new("An error")
यहाँ एक उदाहरण है:
def hello(subject)
raise ArgumentError, "`subject` is missing" if subject.to_s.empty?
puts "Hello #{subject}"
end
hello # => ArgumentError: `subject` is missing
hello("Simone") # => "Hello Simone"
एक कस्टम अपवाद प्रकार बनाना
एक कस्टम अपवाद किसी भी वर्ग है कि फैली हुई है Exception
या का एक उपवर्ग Exception
।
सामान्य तौर पर, आपको हमेशा StandardError
या अवरोही का विस्तार करना चाहिए। Exception
परिवार आमतौर पर वर्चुअल-मशीन या सिस्टम त्रुटियों के लिए होते हैं, उन्हें छुड़ाने से एक मजबूर रुकावट को अपेक्षित रूप से काम करने से रोका जा सकता है।
# Defines a new custom exception called FileNotFound
class FileNotFound < StandardError
end
def read_file(path)
File.exist?(path) || raise(FileNotFound, "File #{path} not found")
File.read(path)
end
read_file("missing.txt") #=> raises FileNotFound.new("File `missing.txt` not found")
read_file("valid.txt") #=> reads and returns the content of the file
अंत में Error
प्रत्यय जोड़कर अपवादों को नाम देना आम है:
-
ConnectionError
-
DontPanicError
हालाँकि, जब त्रुटि स्व-व्याख्यात्मक है, तो आपको Error
प्रत्यय जोड़ने की आवश्यकता नहीं है क्योंकि यह निरर्थक होगा:
-
FileNotFound
बनामFileNotFoundError
-
DatabaseExploded
बनामDatabaseExplodedError
एक अपवाद को संभालना
अपवाद को पकड़ने (बचाव) के लिए स्टार्ट begin/rescue
ब्लॉक का उपयोग करें और इसे संभालें:
begin
# an execution that may fail
rescue
# something to execute in case of failure
end
एक rescue
खंड सी # या जावा जैसी घुंघराले ब्रेस भाषा में catch
ब्लॉक के अनुरूप है।
इस तरह एक नंगे rescue
StandardError
बचाता है।
नोट: डिफ़ॉल्ट StandardError
बजाय Exception
को पकड़ने से बचने के लिए ध्यान रखें। Exception
वर्ग में SystemExit
और NoMemoryError
और अन्य गंभीर अपवाद शामिल हैं जिन्हें आप आमतौर पर नहीं पकड़ना चाहते हैं। इसके बजाय हमेशा StandardError
(डिफ़ॉल्ट) को पकड़ने पर विचार करें।
आप उस अपवाद वर्ग को भी निर्दिष्ट कर सकते हैं जिसे बचाया जाना चाहिए:
begin
# an excecution that may fail
rescue CustomError
# something to execute in case of CustomError
# or descendant
end
यह बचाव खंड किसी भी अपवाद को नहीं पकड़ता है जो कि एक CustomError
नहीं है।
आप अपवाद को एक विशिष्ट चर में भी संग्रहीत कर सकते हैं:
begin
# an excecution that may fail
rescue CustomError => error
# error contains the exception
puts error.message # provide human-readable details about what went wrong.
puts error.backtrace.inspect # return an array of strings that represent the call stack
end
यदि आप एक अपवाद को संभालने में विफल रहे, तो आप इसे किसी भी समय बचाव ब्लॉक में उठा सकते हैं।
begin
#here goes your code
rescue => e
#failed to handle
raise e
end
यदि आप अपने begin
ब्लॉक को पुनः प्राप्त करना चाहते हैं, तो retry
करें:
begin
#here goes your code
rescue StandardError => e
#for some reason you want to retry you code
retry
end
यदि आप प्रत्येक रिट्री में एक अपवाद को पकड़ते हैं, तो आप एक लूप में फंस सकते हैं। इससे बचने के लिए, अपने retry_count
को एक निश्चित संख्या में retry_count
।
retry_count = 0
begin
# an excecution that may fail
rescue
if retry_count < 5
retry_count = retry_count + 1
retry
else
#retry limit exceeds, do something else
end
आप एक else
ब्लॉक या एक ensure
ब्लॉक भी प्रदान कर सकते हैं। अपवाद ब्लॉक के बिना begin
ब्लॉक पूरा होने पर एक else
ब्लॉक निष्पादित किया जाएगा। एक ensure
ब्लॉक को हमेशा निष्पादित किया जाएगा। एक ensure
ब्लॉक सी # या जावा जैसी घुंघराले ब्रेस भाषा में finally
ब्लॉक के अनुरूप है।
begin
# an execution that may fail
rescue
# something to execute in case of failure
else
# something to execute in case of success
ensure
# something to always execute
end
यदि आप किसी def
, module
या class
ब्लॉक के अंदर हैं, तो शुरुआती स्टेटमेंट का उपयोग करने की कोई आवश्यकता नहीं है।
def foo
...
rescue
...
end
कई अपवादों को संभालना
आप एक ही rescue
घोषणा में कई त्रुटियों को संभाल सकते हैं:
begin
# an execution that may fail
rescue FirstError, SecondError => e
# do something if a FirstError or SecondError occurs
end
आप कई rescue
घोषणाएँ भी जोड़ सकते हैं:
begin
# an execution that may fail
rescue FirstError => e
# do something if a FirstError occurs
rescue SecondError => e
# do something if a SecondError occurs
rescue => e
# do something if a StandardError occurs
end
rescue
ब्लॉकों का क्रम प्रासंगिक है: पहला मैच एक निष्पादित है। इसलिए, यदि आप StandardError
को पहली शर्त के रूप में रखते हैं और आपके सभी अपवाद StandardError
से विरासत में मिलते हैं, तो अन्य rescue
कथनों को कभी भी निष्पादित नहीं किया जाएगा।
begin
# an execution that may fail
rescue => e
# this will swallow all the errors
rescue FirstError => e
# do something if a FirstError occurs
rescue SecondError => e
# do something if a SecondError occurs
end
कुछ ब्लॉकों जैसी निहित अपवाद हैंडलिंग है def
, class
, और module
। इन ब्लॉक्स आप छोड़ सकते हैं begin
बयान।
def foo
...
rescue CustomError
...
ensure
...
end
(कस्टम) अपवादों की जानकारी जोड़ना
अपवाद के साथ अतिरिक्त जानकारी शामिल करना, उदाहरण के लिए लॉगिंग उद्देश्यों के लिए या अपवाद पकड़े जाने पर सशर्त हैंडलिंग की अनुमति देने के लिए सहायक हो सकता है:
class CustomError < StandardError
attr_reader :safe_to_retry
def initialize(safe_to_retry = false, message = 'Something went wrong')
@safe_to_retry = safe_to_retry
super(message)
end
end
अपवाद उठाना:
raise CustomError.new(true)
अपवाद को पकड़ना और प्रदान की गई अतिरिक्त जानकारी तक पहुँचना:
begin
# do stuff
rescue CustomError => e
retry if e.safe_to_retry
end