4 Mayıs 2013 Cumartesi

Hata Yakalama

Her programcının yapabileceği hatalar vardır.Ancak bizim bahsedeceğimiz hatalar programınızı çalıştıran kullanıcıların sebep olduğu ve kullanıcının programın çalışmasını engelleyecek türden işlemler yapmasıdır. Python'da yazılan kodun çalıştığı programın kullanıcılarından kaynaklanan hatalar vardır. Ve bu hatalar programın yanlış çalışmasına hatta programın çökmesine sebep olabilir.

Örneğin;
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayıyı Toplayan Program"

Sayi1=int(raw_input("Birinci Sayı"))
Sayi2=int(raw_input("İkinci Sayı"))

print Sayi1+Sayi2
Örnekte de belirtildiği gibi kullanıcının iki sayının toplanması istenmiş ancak kullanıcımız sayı yerine harf girerse program hata verir.Programın verdiği hata mesajı şu şekildedir:
İki Sayıyı Toplayan Program
Birinci Sayı10
İkinci Sayıh
Traceback (most recent call last):
  File "/home/nilay/workspace/Python/ilk.py", line 7, in
    Sayi2=int(raw_input("İkinci Sayı"))
ValueError: invalid literal for int() with base 10: 'h'
Kodda da görüldüğü gibi sayı yerine harf girildiğinde “ValueError” hatası verdi.Yani hata nedeniyle programın son satırı ekrana basılamadı.Bu sebeple programımız çöktü ve işlem yarıda kaldı. Kodu yazarken int() fonksiyonu kullandığımız için kullanıcının girdiği karakter dizisini sayıya dönüştürmeye çalışıyoruz.Örnek verecek olursak;
#!/usr/bin/env python
# -*- coding: utf-8 -*-

sayi=int("7")
print sayi

7
Girilen “7” karakter dizisi görüldüğü gibi sayıya çevrildi.Ancak,
Traceback (most recent call last):
  File "/home/nilay/workspace/Python/ikinci.py", line 4, in
    sayi=int("h")
ValueError: invalid literal for int() with base 10: 'h'
böyle bir örnekte hata oluşuyor.Çünkü program kullanıcıdan aldığı “h” parametresini sayıya çevirmeye çalışıyor ve başarısız oluyor.
Try.......except......
Python'u kullanırken kullanıcının bizim istediğimiz şekilde programı kullanıp kullanamacağını bilemeyiz. Ancak kullanıcıyı yönlendirebiliriz.Önceki yaptığımız örneklerde de kullanıcın yanlış veri girişi bütün programın çökmesine veya durmasına neden olabilir.Bu tür durumlarda Python programı gerekli hata mesajları verip kullanıcıyı uyaracaktır.Tabi bu hata mesajlarını kullanıcı anlamayabilir.O yüzden try....except bloklarını kulanmak daha anlaşılır olacaktır. Yaptığımız ilk örneği ele alacak olursak verdiği hata mesajına tekrar bakalım.
İki Sayıyı Toplayan Program
Birinci Sayı:10
İkinci Sayı:h
Traceback (most recent call last):
  File "/home/nilay/workspace/Python/ilk.py", line 7, in 
    Sayi2=int(raw_input("İkinci Sayı"))
ValueError: invalid literal for int() with base 10: 'h'
Buradaki önemli kısım 'ValueError' hatası vermesidir. Python’da hata yakalama işlemlerinde ilk olarak ne tür bir hata ortaya çıkabileceği tespit edilir. Daha sonra bu hata ile ilgili çözümler üretilir. Buna göre, kullanıcı sayı yerine harf girerse 'ValueError' olarak adlandırılan bir hata meydana gelir.Böyle bir hata ortaya çıkarsa kullanıcıya yaptığı yanlışı görmesini sağlayacak bir hata mesajı verebiliriz.Örneğin, “Sayı Girmelisiniz!” şeklinde belirtebiliriz. Bu konuyla ilgili örnek verecek olursak;
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayıyı Toplayan Program"

Sayi1=int(raw_input("Birinci Sayı"))
Sayi2=int(raw_input("İkinci Sayı"))

print Sayi1+Sayi2
Yanlış veri girildiğinde bu kodun hata vereceğini biliyoruz.Şimdi hata koduna bakalım.
#!/usr/bin/env python
# -*- coding: utf-8 -*-
try:
    print "İki Sayıyı Toplayan Program"
    Sayi1=int(raw_input("Birinci Sayı"))
    Sayi2=int(raw_input("İkinci Sayı"))
    print Sayi1+Sayi2
except ValueError:
    print "Sayı Girmelisiniz.!"
Hata verecek olan kodu try... bloğu içine aldık. except bloğu açıp ne tür bir hata beklediğimizi belirttik.(ValueError)Daha sonra ekranda kullanıcının görmesini istediğimiz mesajı yazdık.Böylece kullanıcı sayı yerine harfe basarsa program çökmeyecek ve çalışmaya devam edecektir.Kullanıcı sayı da girse ,yanlışlıkla harf de girse program ekranda “Sayı Girmelisiniz!” satırı görülür.Yani program yapması gereken işlemleri yapıp programı devam ettirir. Konuyu başka bir örnekle pekiştirelim.Örneğin bir sayıyı 0'a böldüğümüzde hata oluştuğunu gösterelim.
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayının Bölümü"

sayi1=int(raw_input("Birinci Sayı:"))
sayi2=int(raw_input("İkinci Sayı:"))

bolum=float(sayi1/sayi2)
 
print bolum    
Eğer kullanıcı ikinci sayıya 0 girerse şöyle bir hata mesajı oluşur.
İki Sayının Bölümü
Birinci Sayı:10
İkinci Sayı:0
Traceback (most recent call last):
  File "/home/nilay/workspace/Python/ornek.py", line 9, in 
    bolum=float(sayi1/sayi2)
ZeroDivisionError: integer division or modulo by zero
Programımızın hata vereceğini bildiğimiz için ilk olarak nasıl hata verdiğine bakarız.Aldığımız hata türünün “ZeroDivisionError” olduğunu belirledik.Şimdi de hata türüyle ne yapacağımıza karar vermeliyiz.Yine ekranda yazmasını istediğimiz uyarı mesajını belirtelim.
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayının Bölümü"

sayi1=int(raw_input("Birinci Sayı:"))
sayi2=int(raw_input("İkinci Sayı:"))
try:
    bolum=float(sayi1/sayi2)
 
    print bolum         
except ZeroDivisionError:
    print "Bir sayı 0'a bölünemez!"
Bir önceki örneğimizde yaptığımız gibi hata verecek kodları try....bloğu içine yazdık.Burada “ZeroDivisionError” hatası vereceği için except bloğunu da buna göre yazdık.Daha sonra kullanıcının görmesini istediğimiz mesajı yerleştirdik.Böylece programımız çökmeden çalışmaya devam etmiş oldu. Yazılan programlarda önemli olan problemi bulabilmektir.Kullanıcının nasıl davranacağını önceden farkedebilmektir. Yukarıda yaptığımız örnekte de kullanıcı sayı yerine harf girseydi program sadece “ZeroDivisionError” hatası vermezdi.Bunun yanında “ValueError” hatası da verirdi.Bu yüzden her iki hatayı birlikte yakalamamız gerekiyor. Örneğin oluşan hata şöyle olabilir:
İki Sayının Bölümü
Birinci Sayı:10
İkinci Sayı:i
Traceback (most recent call last):
  File "/home/nilay/workspace/Python/ornek.py", line 7, in 
    sayi2=int(raw_input("İkinci Sayı:"))
ValueError: invalid literal for int() with base 10: 'i'
Yukarıdaki kodda sayi2=int(raw_input("İkinci Sayı:")) satırındaki değere yanlış değer girildiği için bolum=float(sayi1/sayi2) satırındaki işlem hata veriyor. Bu nedenle bolum=float(sayi1/sayi2) satırını try... bloğu içine almalıyız.O halde program şu şekilde yazılmalıdır:
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayının Bölümü"

sayi1=int(raw_input("Birinci Sayı:"))
sayi2=int(raw_input("İkinci Sayı:"))
try:
    bolum=float(sayi1/sayi2)
 
    print bolum         
except ZeroDivisionError:
    print "Bir sayı 0'a bölünemez!"
    
except ValueError:
    print "Sayı Girmelisiniz!"
Yukarıdaki kodda görüldüğü gibi hata oluşturacak kodları try... bloğu içine yazdık.Oluşacak hata türlerini de except bloğu içinde ayrı ayrı yazdık.Eğer her iki hata türü içinde hata mesajları aynıysa şu şekilde de gösterebiliriz:
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayının Bölümü"

sayi1=int(raw_input("Birinci Sayı:"))
sayi2=int(raw_input("İkinci Sayı:"))
try:
    bolum=float(sayi1/sayi2)
 
    print bolum         
except (ZeroDivisionError,ValueError):
    print "Bir Hata Oluştu!"
Burada dikkat etmemiz gereken hata türlerini kullanış şeklimizdir.Görüldüğü gibi hata türlerini except'de yakalayıp parantez içinde ve virgülle ayırarak yazıyoruz.Daha sonra da kullanıcının görmesini istediğimiz mesajı yazıyoruz. Python Hata Yakalama konusunda anlattığımız gibi kullanıcının ne istediğini önceden kestirip programımızı daha kullanışlı bir şekilde yazmalıyız.try...except kodu da bize bu konuda yardımcı olacaktır.
Pass Deyimi
Python'da kullanıcıdan kaynaklanan hataları kullanıcıya hissettirmek istemiyorsak “pass” deyimini kullanabiliriz.Bu şekilde program yazılırken karşılaşılan hatalarda hiçbir şey yapmadan programın yoluna devam etmesini sağlıyoruz.
Örneğin;
#!/usr/bin/env python
# -*- coding: utf-8 -*-

print "İki Sayının Bölümü"

sayi1=int(raw_input("Birinci Sayı:"))
sayi2=int(raw_input("İkinci Sayı:"))
try:
    bolum=float(sayi1/sayi2)
 
    print bolum         
except (ZeroDivisionError,ValueError):
    pass
print "Programdaki Hata Gösterilmiyor!"
 

Burada ZeroDivisionError ve ValueError hatasıyla karşılaştığında kullanıcının hiçbir şey farketmeyip programın yoluna devam etmesini sağlıyor.
Eğer programdaki hata önemli ise ve kullanıcının bu hatayı görmesini istiyorsanız bu hatayı pass ile geçiştirmek yerine kullanıcıya hatayla ilgili bir uyarı mesaj gösterebilirsiniz.Ama eğer hatanın kullanıcıya gösterilmesini istemiyorsanız yukarıda belirttiğimiz kodları kullanabilirsiniz.

3 yorum :

  1. #!/usr/bin/env python
    # -*- coding: utf-8 -*-

    print "İki Sayının Bölümü"

    sayi1=int(raw_input("Birinci Sayı:"))
    sayi2=int(raw_input("İkinci Sayı:"))
    try:
    bolum=float(sayi1/sayi2)

    print bolum
    except (ZeroDivisionError,ValueError):
    print "Bir Hata Oluştu!"
    sayi1=int(raw_input("Birinci Sayı:"))
    sayi2=int(raw_input("İkinci Sayı:"))
    bolum=float(sayi1/sayi2)
    print bolum

    Bu şekilde yaptım daha kullanışlı oldu :D

    YanıtlaSil
  2. # -*- coding: utf-8 -*-

    from __future__ import division

    try:
    birincinot=int(raw_input("İlk aldığınız notu giriniz:"))
    ikincinot=int(raw_input("İkinci sınav notunuzu giriniz:"))
    except ValueError:
    print "Lütfen bir sayı giriniz."

    if birincinot < 0 or birincinot > 100 or ikincinot < 0 or ikincinot > 100:
    print "Geçersiz bir not girdiniz."
    a=(birincinot+ikincinot)/2


    if 85<=a<100:
    print 5, "Geçtiniz."
    elif 70<=a<85:
    print 4, "Geçtiniz."
    elif 55<=a<70:
    print 3, "Geçtiniz."
    elif 45<=a<55:
    print 2, "Geçtiniz."
    elif 25<=a<45:
    print 1, "Geçemediniz."
    elif 0<=a<25:
    print 0, "Geçemediniz."

    print "Ortalama puanınız:", a

    Burada bunu yazdığımda hatayı belirttiğimde programın başa dönmesini nasıl sağlayabilirim?

    YanıtlaSil
    Yanıtlar
    1. Bu döngüyü fonksiyon içine yazıp sonucunda return a dediğinde tekrarlama işlemi yapacaktır diye düşünüyorum.

      Sil