یه تابستون متفاوت با یه تصمیم هوشمندانه! دوره هوش مصنوعی یه تابستون متفاوت با یه تصمیم هوشمندانه! دوره هوش مصنوعی
🎯 ثبت نام
بستن تبلیغات
دوره تسلط بر پایتون ؛ آموزش پروژه محور برای حرفه ای ها

با آموزش حضوری و آنلاین مقدماتی تا پیشرفته پایتون , محبوب‌ترین زبان برنامه‌نویسی دنیا در محیطی عملی کاربردی و پروژه محور وارد دنیای برنامه نویسی شوید

مشاهده بیشتر
دوره آموزش ماشین لرنینگ

اگه پایتون بلدی و می‌خوای وارد دنیای هوش مصنوعی بشی، این دوره مخصوص توئه! با آموزش پروژه‌محور و همراهی اساتید حرفه‌ای، یاد بگیر چطور از هوش مصنوعی تو زمینه‌هایی مثل پزشکی، بورس و املاک استفاده کنی.

مشاهده بیشتر
یادگیری عمیق از پایه تا پیشرفته، همراه با پروژه‌های واقعی!

اگه یادگیری ماشین بلدی و آماده‌ای وارد چالش‌های حرفه‌ای بشی، دوره یادگیری عمیق پروژه‌محور برای توئه! طراحی شبکه‌های عصبی و کار روی پروژه‌های واقعی مثل تشخیص تصویر و پردازش زبان رو اینجا یاد می‌گیری.

مشاهده بیشتر
دوره پروژه محور آموزش جنگو

با این دوره، Django رو از پایه شروع کن و به یک حرفه‌ای تبدیل شو! یاد بگیر چطور با معماری MVT، پایگاه داده و RESTful API کار کنی، پروژه‌های واقعی بسازی و آن‌ها رو روی وب سرور مستقر کنی!

مشاهده بیشتر

مدیریت خطا در پایتون / Exception Handling

مدیریت خطا در پایتون / Exception Handling

پایتون دو امکان ویژه برای مدیریت خطاهای پیشبینی نشده در اپلیکیشن ها فراهم کرده و قابلیت های اشکال زدایی (debugging) پرکاربردی به آن ها اضافه می کند.

  • Exception Handling: در آموزش حاضر به تشریح مدیریت خطاها و استثناها خواهیم پرداخت. در زیر لیستی از خطاهای استاندارد از در پایتون را مشاهده می کنید.
  • Assertion ها: این مبحث در آموزش مربوطه ی خود مورد پوشش قرار می گیرد.
اسم خطا
شرح
Exception
کلاس پایه برای تمامی خطاها و exception ها در پایتون
StopIteration
زمانی صادر (raise) می شود که متد next() از کد تکرارکننده (iterator) به هیچ آبجکتی اشاره نکند. در واقع این خطا زمانی رخ می دهد که متد next() از iterator می خواهد اشاره کند که دیگر هیچ مقداری برای تکرار باقی نمانده است.
SystemExit
در نتیجه و به دلیل فراخوانی تابع sys.exit() صادر می شود.
StandardError
کلاس پایه برای تمامی خطاهای درون ساخته به جز StopIteration و SystemExit.
ArithmeticError
کلاس پایه برای تمامی خطاهایی که در نتیجه ی محاسبات عددی رخ می دهد.
OverflowError
زمانی رخ می دهد که خروجی محاسبات از حداکثر یا سقف نوع عددی مورد نظر فراتر رود. در واقع چنانچه نتیجه ی عملیات ریاضی و محاسبات بیش از حد قابل ارائه و نمایش باشد (بزرگ تر از ظرفیت نوع عددی مورد نظر و غیر قابل نمایش توسط این type باشد)، این خطا فراخوانی می شود.
FloatingPointError
این خطا زمانی بروز می دهد که عملیات ممیز شناور با شکست مواجه شود.
ZeroDivisionError
Raised when division or modulo by zero takes place for all numeric types.زمانی صادر می شود که عملیات تقسیم بر صفر برای انواع عددی رخ دهد. به عبارت دیگر این خطا زمانی رخ می دهد که آرگومان دوم یک عملیات تقسیم یا modulo عدد صفر باشد.
AssertionError
زمانی صدا زده می شود که دستور Assert (انتظار نتیجه ی مد نظر را در تست داشتن) با خطا مواجه شود.
AttributeError
Raised in case of failure of attribute reference or assignment.زمانی صدا زده می شود که attribute reference/assignment با خطا مواجه شود.
EOFError
این خطا هنگامی رخ می دهد که ورودی از تابع raw_input() یا input() دریافت نشده و نیز پایتون به انتهای فایل رسیده در حالی که قطعه مربوطه به طور صحیح بسته نشده باشد.
ImportError
زمانی رخ می دهد که دستور import با موفقیت اجرا نشود.
KeyboardInterrupt
هنگامی رخ می دهد که کاربر روند اجرای برنامه را، اغلب با فشردن همزمان کلیدهای Ctrl+c، مختل نماید.
LookupError
Base class for all lookup errors.کلاس پایه برای تمامی خطاهای مربوط به lookup. در واقع این خطا هنگامی رخ می دهد که یک کلید یا اندیس مورد استفاده در mapping یا sequence مجاز و معتبر نباشد.
IndexError
KeyError
زمانی رخ می دهد که اندیس در sequence (رشته ها، لیست ها یا تاپل ها) مورد نظر وجود نداشته و یافت نشود.هنگامی صدا زده می شود که کلید مشخص شده در نوع داده ای dictionary موجود نباشد.
NameError
زمانی رخ می دهد که یک شناسه (identifier) در فضای نامی یا namespace محلی یا سراسری یافت نشود.
UnboundLocalError
EnvironmentError
زمانی صدا زده می شود که پایتون سعی داشته باشد به یک متغیر محلی در بدنه ی تابع یا متد دسترسی داشته باشد اما این متغیر مقداردهی نشده باشد.
کلاس پایه تمامی خطاهایی که خارج از محیط پایتون رخ می دهد.
IOError
IOError
زمانی صادر می شود که عملیات ورودی/خروجی با شکست مواجه شود مانند زمانی که دستور print اجرا شده یا تابع open() برای باز کردن فایل فراخوانی شود که اصلا وجود ندارد.
به هنگام بروز خطاهای مربوط به سیستم عامل رخ می دهد
SyntaxError
IndentationError
زمانی که خطای دستور نحوی و syntax در کد وجود داشته باشد، رخ می دهد.
کلاس پایه برای تمامی خطاهای ساختار نحوی (سینتکس) مربوطه توگذاری و indentation.
SystemError
زمانی رخ می دهد که مفسر با مشکل داخلی مواجه شود. لازم به ذکر است که به هنگام رخداد این خطا، مفسر پایتون از کد خارج نمی شود.
SystemExit
این خطا به سبب فراخوانده شدن متد sys.exit() صادر می شود. اگر این خطا در کد / با کدنویسی مدیریت نشود، باعث می شود که مفسر از کد برنامه خارج شود.
TypeError
زمانی صادر می شود که یک عملیات یا تابع بر روی آبجکتی از نوع نامربوط اعمال شود.
ValueError
چنانچه عملیات یا تابع درون ساخته ای آرگومانی از نوع صحیح اما با مقدار غلط دریافت کند، خطای جاری رخ می دهد.
RuntimeError
هنگامی صادر می شود که خطا در زمان اجرا رخ داده و به هیچ یک از گروه های تعریف شده از خطا تعلق نداشته باشد. مقدار مربوطه یک رشته ی متنی است که اشاره می کند دقیقا چه مشکلی رخ داده است.
NotImplementedError
Raised when an abstract method that needs to be implemented in an inherited class is not actually implemented.
خطای جاری زمانی رخ می دهد که متد abstract که بایستی داخل کلاس به ارث برده شده پیاده سازی شده باشد، بدنه ی آن طبق انتظار تعریف و پیاده سازی نشده باشد.
به عبارت دیگر، این خطا را متدهای abstract که بدنه آن ها داخل کلاس های مشتق شده پیاده سازی نشده باشد، صدا زده می شود.

Assertion ها (دستورات assert و بررسی صحت شرط) در پایتون

assertion یک تست sanity-check یا تست ساده جهت بررسی معقولانه بودن ادامه ی فرایند تست می باشد. دستورات assert انتظار دارند که نتیجه ی عبارت صحیح باشد و مقدار true را برگرداند و چنانچه شرط برقرار نبود، یک خطا صادر می شود.

جهت درک آسان مفهوم assertion در پایتون، می توان آن را به دستور raise-if (یا به عبارت دقیق تر raise-if-not) تشبیه کرد. در این سناریو یک عبارت تست شده و صحت آن بررسی می شود. اگر نتیجه غلط بوده و خروجی مورد انتظار تولید نشد، یک خطا صادر می شود.

برای اجرای تست های assertion در اپلیکیشن، کافی است از دستورات assert استفاده نمایید. این کلیدواژه از ویرایش 1.5 به بعد زبان پایتون برای برنامه نویس قابل استفاده می باشد.برنامه نویسان معمولا دستورات assert را در ابتدای یک تابع قرار داده تا معتبر یا مجاز بودن ورودی را بررسی کند و نیز یک دستور assert دیگر جهت بررسی صحت خروجی تابع فراخوانی شده (در انتها و پس از صدا زدن تابع)، درج می کنند.

دستور assert

زمانی که پایتون در حین خواندن و تفسیر کد با دستور assert مواجه می شود، مفسر آن عبارت همراه را بررسی کرده که طبق انتظار باید صحیح باشد. اگر عبارت false بود، پایتون خطای AssertionError را صادر می کند.

نحوه ی استفاده از assert در زیر نمایش داده شده است:

1
assert Expression[, Arguments]<button></button>

اگر نتیجه ی expression یا عبارتی که پس از دستور assert درج می شود false بود (assertion ناموفق بود)، پایتون ArgumentExpression را به عنوان پارامتر برای AssertionError مورد استفاده قرار می دهد. خطاهای AssertionError را می توان به راحتی با استفاده از دستور try-except مدیریت کرد. اما اگر آن را مدیریت نکرده باشید، سبب می شوند برنامه خاتمه یافته و یک traceback (بازتاب مجموعه خطاهای تولید شده که به صورت پشته بر روی هم قرار گرفته اند) تولید شود.

مثال

در زیر تابعی را مشاهده می کنید که دما را از مقیاس کلوین به فارنهایت تبدیل می کند. از آنجایی که 0 درجه کلوین سردترین نقطه است، تابع اگر با مقدار منفی مواجه شود، خطا می دهد.

1
2
3
4
5
6
7
8
#!/usr/bin/python
def KelvinToFahrenheit(Temperature):
   assert (Temperature >= 0),"Colder than absolute zero!"
   return ((Temperature-273)*1.8)+32
print KelvinToFahrenheit(273)
print int(KelvinToFahrenheit(505.78))
print KelvinToFahrenheit(-5)
<button></button>

کد بالا پس از اجرا، نتیجه ی زیر را بدست می دهد:

1
2
3
4
5
6
7
8
9
32.0
451
Traceback (most recent call last):
File "test.py", line 9, in
print KelvinToFahrenheit(-5)
File "test.py", line 4, in KelvinToFahrenheit
assert (Temperature >= 0),"Colder than absolute zero!"
AssertionError: Colder than absolute zero!
<button></button>

Exception (خطای زمان اجرا و پیشبینی نشده) چیست؟

Exception یک رخداد (event) است که در طول اجرا برنامه رخ می دهد و روند اجرای برنامه را مختل می نماید. در کل، زمانی که اسکریپت پایتون با شرایطی که قابلیت مدیریت آن را ندارد، مواجه می شود، یک خطا صادر می کند. exception در پایتون یک آبجکت پایتون است که نماینده ی خطا می باشد.

زمانی که اسکریپت پایتون یک خطا (exception) صادر می کند، یا باید خطا را مدیریت کند و یا برنامه را به طور کلی ببندد.

مدیریت Exception (خطا)

در صورت مواجه با کد مشکوک که ممکن است سبب رخداد خطا شود، می توانید آن را داخل بدنه ی try: قرار دهید. پس از بدنه ی try:، یک دستور except: در متن برنامه درج کرده و به دنبال آن قطعه کدی که مشکل برنامه را به صورت بهینه اداره می کند، تایپ نمایید.

نحوه ی استفاده از دستور

در زیر نحوه ی بکار بردن دستور try …except … else را مشاهده می کنید:

در زیر نکات آموزشی مهمی در خصوص ساختار فوق عنوان شده است:

  • یک دستور try واحد می تواند چندین دستور متناظر except داشته باشد. این ویژگی به خصوص زمانی مفید واقع می شود که بدنه ی try حامل دستورات متعددی باشد که ممکن است هر یک خطای متفاوتی را سبب شود.
  • می توانید یک عبارت except سراسری (generic) تنظیم کنید که هر خطایی را به راحتی مدیریت نماید.
  • می توانید پس از دستور یا دستورات except، عبارت else را مورد استفاده قرار دهید. چنانچه کد موجود در بدنه ی try: خطا نداد، آنگاه قطعه کد else اجرا می شود.
  • قطعه کد else جای مناسبی برای تعریف کدهایی می باشد که احتمالا مشکلی برای کل برنامه ایجاد نکرده و اجرای بدون خطای آن حتمی است.
مثال

کد زیر سعی دارد ابتدا یک فایل را باز کند و سپس در آن اطلاعاتی را درج نماید. از آنجایی مجوز در سطح نوشتن و درج داده های جدید داخل فایل اعطا نشده، خطای مربوطه توسط قطعه کد except صادر می شود.

1
2
3
4
5
6
7
8
9
#!/usr/bin/python
try:
   fh = open("testfile", "r")
   fh.write("This is my test file for exception handling!!")
except IOError:
   print "Error: can\'t find file or read data"
else:
   print "Written content in the file successfully"
<button></button>

کد بالا خروجی زیر را ارائه می دهد:

1
Error: can't find file or read data<button></button>

عبارت except بدون مشخص کردن نوع خطا

می توانید از دستور except که هیچ خطا یا exception ای در آن تعریف نشده نیز به صورت زیر استفاده نمایید و در واقع چنانچه هر گونه خطایی وجود داشت، دستور موجود در قطعه کد except را انجام دهد:

1
2
3
4
5
6
7
8
9
10
11
12
try:
   You do your operations here;
   ......................
سعی کن یک عملیاتی را در اینجا انجام دهی
except:
   If there is any exception, then execute this block.
در صورت برخورد با خطا،  عملیات دیگری را انجام بده
   ......................
else:
   If there is no exception then execute this block.
در غیر این صورت این کار را انجام بده
<button></button>

این نوع دستور try-except تمامی خطاهایی که در برنامه رخ می دهد را گرفته و مدیریت می نماید. با این حال استفاده از این تکنیک در برنامه نویسی به هیچ وجه توصیه نمی شود چرا که تمامی خطاها را اداره می کند اما در ریشه یابی خطا و شناسایی اصل مشکل هیچ کمکی به توسعه دهنده نمی کند.

عبارت except با چندین Exception

می توانید با یک دستور except همزمان چندین exception را به صورت زیر مدیریت نمایید:

1
2
3
4
5
6
7
8
9
10
11
12
13
try:
   You do your operations here;
عملیاتی را در این قطعه کد امتحان نمایید
   ......................
except(Exception1[, Exception2[,...ExceptionN]]]):
   If there is any exception from the given exception list,
   then execute this block.
در صورت مواجه شدن با خطا، کارهای تعریف شده در این بخش را اجرا نمایید
   ......................
else:
   If there is no exception then execute this block.
اگر خطایی نبود، دستورات این بخش را اجرا کن
<button></button>

استفاده از ساختمان try-finally جهت مدیریت خطا

می توانید در انتهای قطعه کد try: از finally: نیز استفاده نمایید. دستوری که در بدنه ی finally: قرار می گیرد، صرف نظر اینکه خطایی در قطعه ی try رخ داده یا خیر، به طور قطع اجرا می شود. نحوه ی استفاده از این ساختار در زیر نمایش داده شده است:

1
2
3
4
5
6
7
8
9
10
11
try:
   You do your operations here;
عملیات را در اینجا انجام دهید
   ......................
   Due to any exception, this may be skipped.
ممکن است به دلیل وجود هر گونه خطایی این کد اجرا نشود
finally:
   This would always be executed.
دستوری که حتما اجرا خواهد شد
   ......................
<button></button>

نمی توانید عبارت else و finally را یکجا بکار ببرید.

مثال
1
2
3
4
5
6
7
#!/usr/bin/python
try:
   fh = open("testfile", "w")
   fh.write("This is my test file for exception handling!!")
finally:
   print "Error: can\'t find file or read data"
<button></button>

اگر مجوز باز کردن فایل در سطح درج اطلاعات در آن را نداشته باشید، در آن صورت نتیجه ی زیر حاصل می گردد:

1
Error: can't find file or read data<button></button>

مثال فوق را می توان به صورت کارا و مختصرتر نیز، همچون نمونه کد زیر، نوشت:

1
2
3
4
5
6
7
8
9
10
11
#!/usr/bin/python
try:
   fh = open("testfile", "w")
   try:
      fh.write("This is my test file for exception handling!!")
   finally:
      print "Going to close the file"
      fh.close()
except IOError:
   print "Error: can\'t find file or read data"
<button></button>

زمانی که سیستم در بدنه ی try با مشکل مواجه شده و خطای مربوطه را صادر کرد، اجرا سریعا به قطعه کد finally انتقال می یابد. پس از اینکه کلیه ی دستورات موجود در بدنه ی finally اجرا شدند، خطای مزبور بار دیگر رخ داده، ولی این بار در لایه ی بالاتر دستور try-except بعدی، به واسطه ی دستورات except مدیریت می شود.

آرگومان ارسال شده به Exception

یک exception می تواند آرگومان (argument) نیز داشته باشد. آرگومان پاس داده شده به exception، اطلاعات بیشتری را درباره ی خطای رخ داده ارائه می دهد. محتوای آرگومان می تواند با توجه به نوع خطا متفاوت باشد. می توانید با لحاظ کردن یک متغیر ساده در عبارت except، مانند زیر، آرگومانی را به exception ارسال نمایید:

1
2
3
4
5
6
try:
   You do your operations here;
   ......................
except ExceptionType, Argument:
   You can print value of Argument here...
<button></button>

اگر کدی بنویسید که تنها یک خطا (exception) را مدیریت کند، در آن صورت کافی است یک متغیر پس از اسم خطا، در دستور except، لحاظ نمایید. چنانچه لازم است چندین خطا را گیر انداخته و مدیریت نمایید، در آن صورت می توانید متغیری پس از چندتایی exception خطا (متغیر exception از نوع چندتایی یا tuple) لحاظ نمایید.

این متغیر مقدار خطا که یک رشته باشد را گرفته و در واقع دلیل بروز خطا را در خود ذخیره می کند. این متغیر می تواند یک مقدار را دریافت کند یا همزمان چندین مقدار را در قالب یک چندتایی (tuple) در خود نگه دارد. این متغیر چندتایی (از نوع tuple) اغلب حامل رشته ی متنی خطا، شماره ی خطا و محل رخداد آن می باشد.

مثال

مثال زیر تنها یک خطا را مدیریت می کند.

1
2
3
4
5
6
7
8
9
10
#!/usr/bin/python
# Define a function here.
def temp_convert(var):
   try:
      return int(var)
   except ValueError, Argument:
      print "The argument does not contain numbers\n", Argument
# Call above function here.
temp_convert("xyz");
<button></button>

نتیجه ی زیر را بدست می دهد:

1
2
3
The argument does not contain numbers
invalid literal for int() with base 10: 'xyz'
<button></button>

تعریف و مدیریت خطا با استفاده از دستور raise

می توانید با استفاده از دستور raise خطاهای متعددی را مدیریت کنید. سینتکس و ساختار نحوی کلی برای مدیریت خطا با استفاده از دستور raise در زیر نمایش داده شده است.

ساختارکلی و نحوه ی استفاده از raise

1
raise [Exception [, args [, traceback]]]<button></button>

در اینجا، پارامتر Exception در واقع نوع خطا (برای مثال NameError) و پارامتر argument یک مقدار است که به آرگومان exception یا خطا ارسال می شود. پارامتر argument کاملا اختیاری است و در صورت عدم ارسال مقداری به آن، آرگومان مزبور برابر None خواهد بود.

آخرین آرگومان، traceback، نیز اختیاری است و در واقع به ندرت مورد استفاده قرار می گیرد. این آرگومان پشته ای از خطاها و یک آبجکت traceback هست که مربوط به خطای مورد نظر می باشد.

مثال

exception می تواند یک رشته، کلاس و یا آبجکت باشد. اغلب خطاهایی که Python core صادر می کند از جنس کلاس هستند و یک آرگومان نیز دارند که نمونه ای از آن کلاس می باشد. تعریف خطاهای جدید امری بسیار آسان است و به راحتی زیر قابل پیاده سازی می باشد:

1
2
3
4
5
6
def functionName( level ):
   if level < 1:
      raise "Invalid level!", level
      # The code below to this would not be executed
      # if we raise the exception
<button></button>
نکته:

جهت گرفتن و مدیریت خطا، عبارت "except" بایستی به همان خطایی که آبجکت، کلاس یا رشته ی ساده صادر کرده، اشاره کند. برای مثال، جهت گرفتن و ضبط خطای فوق، لازم است دستور except را به صورت زیر تنظیم نمایید:

1
2
3
4
5
6
7
try:
   Business Logic here...
except "Invalid level!":
   Exception handling here...
else:
   Rest of the code here...
<button></button>

خطاهای اختصاصی و user-defined

پایتون به توسعه دهنده این امکان را می دهد تا خطاهای دلخواه خود را تعریف کند. برای این منظور می بایست از کلاس های درون ساخته ی exception ارث بری نماید.

در زیر مثالی را مشاهده می کنید که در آن یک خطای زمان اجرا و مربوط به RuntimeError رخ داده است. در مثال حاضر، یک کلاس تعریف شده که این کلاس خود از کلاس پایه ی RuntimeError مشتق (subclass) شده است. چنانچه لازم است اطلاعات بیشتری در خصوص خطای رخ داده برای کاربر نمایش دهید، توصیه می شود از این روش استفاده نمایید.

در بدنه ی دستور try: خطاهای اختصاصی (user-defined exception) تعریف (raise) شده و سپس این خطا داخل ساختمان except ضبط و مدیریت (catch) می شود. متغیر e در واقع یک آبجکت یا نمونه ای ساخته شده از روی کلاس Networkerror می باشد.

1
2
3
4
class Networkerror(RuntimeError):
   def __init__(self, arg):
      self.args = arg
<button></button>

زمانی که کلاس فوق را تعریف کردید، آنگاه می توانید خطا را به صورت زیر اعلان و پیاده سازی کنید:

1
2
3
4
5
try:
   raise Networkerror("Bad hostname")
except Networkerror,e:
   print e.args
<button></button>
1396/02/14 21336 3849
رمز عبور : tahlildadeh.com یا www.tahlildadeh.com
نظرات شما

نظرات خود را ثبت کنید...