عبارت try

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

  • یک قسمت try با یک یا چند قسمت except
  • یک قسمت try با فقط و فقط یک قسمت finally

try/except

گرامر try/except از عبارت try به شکل زیر است :

try:
    statement(s)
except [expression [, target]]:
    statement(s)
[else:
    statement(s)]


عبارت try شامل یک یا چند بخش except و بخش اختیاری else است. بدنه بخش except به عنوان گرداننده استثناء 1 شناخته می شود و در زمانی که expression در قسمت except با یک شی استثناء که در قسمت try ایجاد شده مطابقت کند ، اجرا می شود . expression یک کلاس اختیاری یا تاپلی از کلاس هایی است که با هر شی استثنائی ، که یکی از کلاس های لیست شده یا هر یک از زیر کلاس های آنها می باشد مطابقت دارد. قسمت اختیاری target شناسه ای است که پیتون آنرا به شی استثناء متصل کند ، درست قبل اجرا شدن کد except . به زبان ساده تر این شناسه نمونه ای از شی استثنای رها شده در قسمت try است. همچنین یک گرداننده می تواند با فراخوانی تابه exc_info از ماژول sys به شی استثناء دسترسی یابد .

مثال:

try: 1/0
except ZeroDivisionError: print "caught divide-by-0 attempt"


اگر قسمت try شامل چندین except شود ، مکانیزم خطایاب بخش های except را به گونه ای امتحان می کند که اولین except که expression آن با شی استثناء مطابقت داشت به عنوان گرداننده انتخواب می شود. بنابراین شما باید گرداننده های مخصوص را همیشه قبل از به کار بردن گرداننده عمومی ، به کار گیرید زیرا در غیر این صورت گرداننده خاص تر که بعد از گرداننده عمومی آمده است هرگز اجرا نخواهد شد . آخرین بخش except ممکن است فاقد قسمت expression باشد ، این بخش گرداننده هر استثنائی که به این مرحله برسد، خواهد بود. چنین گرداننده های بی شرطی کمتر نیاز می شوند. باید توجه داشت که انتشار استثناء زمانی که گرداننده نضیر آن یافت شود خاتمه می یابد.بنابراین اگر یک عبارت try به صورت تو ر تو بایک عبارت try دیگر بیاید، گرداننده هایی که توسط عبارت try داخلی ایجاد شده اند در اولویت قرار دارند و اگر یکی از آنها انتخاب شوند تنها گرداننده خواهند بود و دیگر نوبت به گرداننده های عبارت try خارجی نخواهد رسید. برای مثال:

    try: 1/0
    except: print "caught an exception"
except ZeroDivisionError:
    print "caught divide-by-0 attempt"
# prints: caught an exception

در این مورد اهمیتی ندارد که قسمت گرداننده ZeroDivisionError: در try خارجی خاص تر از گرداننده عمومی در try داخلی است زیرا این بخش حتی به مرحله اجرا نیز نمی رسد . چون ایجاد استثناء پس از رسیدن به گرداننده داخلی پایان می یابد. اما قسمت اختیاری else از ساختار try/except تنها در زمانی اجرا می شود که قسمت try به صورت نرمال و بدون خطا پایان یابد. به زبان ساده تر این بخش زمانی که در قسمت try شی استثنائی ایجاد شود یا اجرای برنامه از قسمت try با عباراتی نظیر return , break و یا continue خارج شود ، اجرا نمی شود. قسمت else برای پرهیز ار رسیدگی تصادفی به استثناهای غیر منتظره مفید است برای مثال:

 

print repr(value), "is ",
try:
    value + 0
except TypeError:
    # not a number, maybe a string, Unicode, UserString...?
    try:
        value + ''
    except TypeError:
        print "neither a number nor a string"
    else:
        print "a string or string-like value"
else:
    print "a number of some kind"


try/finally

گرامر ساختار try/finally از عبارت try به این شکل است:

 

try:
    statement(s)
finally:
    statement(s)

این ساختار فقط می تواند یک بخش finally داشته باشد و نمی تواند شامل else شود.

ازعبارت finally به عنوان گرداننده پاکسازی یاد می شود. اگر عبارت try با ایجاد شی استثناء پایان پذیرد قسمت finally اجرا می شود و شی استثناء نیز باقی می ماند ، اگر عبارت try به صورت عادی پایان پذیرد باز هم finally اجرا خواهد شد حتی اگر اجرای برنامه از قسمت try با استفاده از عباراتی نظیر return, break و یا continue خارج شود.

try/finally راهی محکم و واضح برای اجرای کد پایانی است که در هر شرایطی اجرا خواهد شد. این کار برای استحکام بخشیدن به برنامه بسیار مفید است . ( مخصوصا برای کار کردن با منابع خارجی از قبیل فایل ها ، بانک اطلاعاتی ، شبکه و...)

مثال:

 

f = open(someFile, "w")
try:
    do_something_with_file(f)
finally:
    f.close(  )

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

finally نمی تواند شامل continue باشد ولی در این قسمت می توان برای خاتمه دادن به شی استثناء از عبارات return و یا break استفاده کرد. البته این امر باعث نا خوانایی کد شما می شود.

 

 


منابع:

  • بر گرفته شده از کتاب O'Reilly Python in a Nutshell

صفحه قبلی: پایتون
صفحه بعدی: PyGTK