İçeriğe geç

Menü

Berk Akademi
Yorumlar Google yorumları Birebir ders başvurusu Ücretsiz ön görüşme Ana Sayfa

Python try, except, else ve finally Farkı Nedir? Örneklerle

python-try-except-else-finally-farki
Bu yazıda neler var?
  1. try ve except: Hatayı Belirli Türle Yakalamak
  2. else Bloğu Ne Zaman Çalışır?
  3. finally ve return: Temizlik Adımı Akışı Nasıl Etkiler?
  4. Aynı Fonksiyonla Üç Akış: Hatalı Giriş, Başarılı Giriş ve Kaynak Kapatma
  5. Hangi Durumda Hangi Blok Çalışır? Karar Tablosu
  6. try-except Yazarken Sık Yapılan Hatalar
  7. Sık Sorulan Sorular

Python'da try, except, else ve finally dört ayrı iş yapar. try hata çıkarabilecek kodu dener, except yakalanan hatayı ele alır, else yalnızca try hatasız bittiğinde çalışır, finally ise hata olsa da olmasa da çalışan temizlik adımıdır. Bu yazıda ilk ikisini kısa kodlarla deneyeceksin; finally ve karar tablosu sonraki bölümlerde.

try ve except: Hatayı Belirli Türle Yakalamak

try içine hata çıkabilecek tek bir iş yaz, except ile de o işin vereceği hata türünü yakala. Python'da int("abc") gibi sayıya çevrilemeyen bir metin ValueError fırlatır. Bu hata yakalanmazsa program çöker; yakalanırsa akış except bloğuna geçer.

try:
    sayi = int("abc")
    print("Sayı:", sayi)
except ValueError:
    print("Geçerli bir tam sayı girmedin.")

Beklenen çıktı:

Geçerli bir tam sayı girmedin.

İlk satırdaki dönüştürme hata verdiği için print("Sayı:", sayi) hiç çalışmaz. Hata türü ValueError olduğundan except devreye girer.

Birden fazla except: sıra önemlidir

Python except bloklarını yukarıdan aşağıya sırayla dener ve hatayla uyuşan ilk blokta durur; kalanlara bakmaz. Bu yüzden özel türler üstte, geniş tür olan Exception en altta durmalıdır.

def bol(a, b):
    try:
        return int(a) / int(b)
    except ValueError:
        print("Sayı girmelisin.")
    except ZeroDivisionError:
        print("Sıfıra bölemezsin.")
    except Exception as hata:
        print("Beklenmeyen hata:", hata)

print(bol("10", "abc"))
print(bol("10", "0"))
print(bol("10", "2"))

Beklenen çıktı:

Sayı girmelisin.
None
Sıfıra bölemezsin.
None
5.0

Hata yakalanan çağrılarda fonksiyon return satırına ulaşamadığı için None döner. Exception bloğunu en üste yazsaydın her hata ona takılırdı ve alttaki özel bloklar hiç çalışmazdı. Geniş yakalamayı yalnızca son çare olarak tut ve hatayı en azından yazdır ya da kaydet; sessizce yutmak, hatanın nedenini bulmayı zorlaştırır.

else Bloğu Ne Zaman Çalışır?

else Bloğu Ne Zaman Çalışır?

else yalnızca try bloğu hiç hata vermeden bittiğinde çalışır. Hata çıkarsa else atlanır ve ilgili except devreye girer. Önemli ayrıntı şu: else içinde çıkan bir hata, aynı try'ın except bloklarına takılmaz; yakalanmadan yukarı çıkar.

Bu yüzden iyi bir kural vardır: yalnızca hata verebilecek satır try'da, başarılı olduktan sonra yapılacak işler else'te durur. Farkı bir örnekle görelim. Önce her şeyi try içine yazan sürüm:

import math

def kok_a(metin):
    try:
        sayi = int(metin)
        print("Kök:", math.sqrt(sayi))
    except ValueError:
        print("Geçersiz sayı.")

kok_a("-4")

Beklenen çıktı:

Geçersiz sayı.

"-4" geçerli bir tam sayıdır; asıl hatayı math.sqrt verir, o da ValueError türündedir. Except bu hatayı yanlışlıkla yakalar ve mesaj yanıltıcı olur. Şimdi else kullanan sürüm:

def kok_b(metin):
    try:
        sayi = int(metin)
    except ValueError:
        print("Geçersiz sayı.")
    else:
        print("Kök:", math.sqrt(sayi))

kok_b("16")
kok_b("abc")
kok_b("-4")

Beklenen çıktı:

Kök: 4.0
Geçersiz sayı.
Traceback (most recent call last):
  ...
ValueError: ...

Önce "16" için dönüştürme başarılı olur ve else çalışır. "abc" için except devreye girer, else atlanır. "-4" için dönüştürme başarılıdır, ancak else içindeki math.sqrt hata verir ve bu hata except'e takılmadan görünür olur. Hata mesajının ayrıntısı Python sürümüne göre değişebilir; önemli olan hatanın gizlenmemesidir.

finally ve return: Temizlik Adımı Akışı Nasıl Etkiler?

finally bloğu hata çıksa da çıkmasa da çalışır. try ya da except içinde return olsa bile fonksiyon geri dönmeden hemen önce finally çalıştırılır.

def deneme():
    try:
        print("try çalıştı")
        return "try'dan dönen değer"
    finally:
        print("finally çalıştı")

print(deneme())

Beklenen çıktı:

try çalıştı
finally çalıştı
try'dan dönen değer

Önce try içindeki print çalışır. return satırına gelince dönecek değer hazırlanır, ama fonksiyon henüz bitmez; Python önce finally bloğunu çalıştırır. Dışarıdaki print değeri en son görür, bu yüzden değer çıktının son satırında görünür.

finally içine return yazma tuzağı

Python dokümantasyonuna göre finally bloğu bir return çalıştırırsa bekleyen istisna iptal edilir. Hata sessizce kaybolur.

def tuzak():
    try:
        raise ValueError("Bir sorun var")
    finally:
        return "finally döndü"

print(tuzak())

Beklenen çıktı:

finally döndü

raise bir ValueError başlatır, ama finally içindeki return o hatayı iptal eder. Program çökmez, hata mesajı da görünmez. Bu yüzden finally yalnızca temizlik için kullanılır: dosya kapatmak, bağlantıyı bırakmak gibi.

Aynı Fonksiyonla Üç Akış: Hatalı Giriş, Başarılı Giriş ve Kaynak Kapatma

Aynı Fonksiyonla Üç Akış: Hatalı Giriş, Başarılı Giriş ve Kaynak Kapatma

Dört bloğu tek fonksiyonda görelim:

def sayiya_cevir(metin):
    try:
        sayi = int(metin)
    except ValueError:
        print("Hata: sayıya çevrilemedi")
        return None
    else:
        print("Başarılı: çevrildi")
        return sayi
    finally:
        print("Çeviri denemesi bitti")

print(sayiya_cevir("abc"))
print(sayiya_cevir("42"))

Beklenen çıktı:

Hata: sayıya çevrilemedi
Çeviri denemesi bitti
None
Başarılı: çevrildi
Çeviri denemesi bitti
42

Akış 1 ("abc"): int("abc") ValueError üretir. except hata mesajını yazar. else atlanır, çünkü yalnızca hata çıkmazsa çalışır. finally mesajı yazılır ve None döner.

Akış 2 ("42"): Çevirme başarılıdır, except atlanır. else başarı mesajını yazar, finally kendi mesajını yazar, 42 en son döner.

Akış 3: dosyayı finally ile kapatmak

def ilk_satiri_oku(yol):
    dosya = None
    try:
        dosya = open(yol, encoding="utf-8")
        return dosya.readline()
    except FileNotFoundError:
        print("Dosya bulunamadı")
        return ""
    finally:
        if dosya is not None:
            dosya.close()
            print("Dosya kapatıldı")

print(ilk_satiri_oku("yok.txt"))

Beklenen çıktı ("yok.txt" diye bir dosya yoksa; son satır, boş metnin yazdırdığı boş satırdır):

Dosya bulunamadı

open() dosyayı bulamazsa FileNotFoundError verir ve dosya değişkenine hiçbir şey atanmaz. Bu yüzden değişkene baştan None veriyoruz. finally içinde None olup olmadığına bakmasaydık, olmayan bir dosyayı kapatmaya çalışıp yeni bir hata alırdık. Dosya varsa önce "Dosya kapatıldı" yazılır, ardından okunan satır ekrana gelir.

Aynı işi with ifadesi çok daha kısa yapar: with open(yol, encoding="utf-8") as dosya: yazdığında dosya, bloktan çıkınca hata olsa bile otomatik kapanır. Elle finally yazmanın kısa karşılığıdır; yine de dosyanın bulunamaması gibi hataları except ile yakalaman gerekir.

Hata yönetimini küçük alıştırmalarla pekiştirmek istersen birebir Python dersleri kapsamında bu yapıları kişiye özel ödevlerle çalışabilirsin.

Hangi Durumda Hangi Blok Çalışır? Karar Tablosu

Aşağıdaki tabloda her bloğun içinde birer print satırı olduğunu varsay. Tablo, hangi durumda hangi blokların çalıştığını ve ekrana ne çıktığını gösterir.

DurumÇalışan bloklarEkrana çıkan sonuç
Hata yoktry, else, finallytry, else ve finally çıktıları sırayla görünür; program devam eder.
Eşleşen hata vartry'ın hata öncesi kısmı, except, finallyHatadan önceki try çıktısı, except mesajı ve finally çıktısı görünür; program devam eder.
Eşleşmeyen hata vartry'ın hata öncesi kısmı, finallyHatadan önceki try çıktısı ve finally çıktısı görünür; ardından hata yukarı çıkar, yakalayan yoksa hata mesajı (traceback) yazılır ve program durur.
else içinde hata vartry, else'in hata öncesi kısmı, finallytry çıktısı, hatadan önceki else çıktısı ve finally çıktısı görünür; hata aynı try'ın except bloklarınca yakalanmadan çıkar.
try içinde return vartry, finallytry ve finally çıktıları görünür, ardından değer döner; else çalışmaz.

Tabloyu okurken önce finally sütununa bak: her satırda yer alır. except ile else ise aynı çalıştırmada birlikte görünmez; biri hata olduğunda, diğeri hata olmadığında devreye girer.

try-except Yazarken Sık Yapılan Hatalar

  • Gereğinden geniş except Exception kullanmak: Her hatayı aynı kovaya atar ve hatanın gerçekte hangi türde olduğunu görmeni engeller. Beklediğin türü yaz (ValueError, ZeroDivisionError gibi). Geniş yakalama gerekiyorsa mesajı yazdır ya da kayda al.
  • Çıplak except ya da except içinde pass yazmak: Hatayı sessizce geçer, program yanlış çalışsa bile iz kalmaz. Python dokümantasyonuna göre Exception, BaseException sınıfının altındadır; KeyboardInterrupt ve SystemExit ise Exception kapsamında değildir. Çıplak except bunları da yakalar, bu yüzden Ctrl+C ile programı durdurmak bile zorlaşabilir. Hatayı susturma; mesajı yazdır, kayda al ya da raise ile yeniden fırlat.
  • try içine çok fazla satır koymak: Hatanın hangi satırdan geldiği belirsizleşir ve ilgisiz bir hata yanlış except tarafından yakalanabilir. Yalnızca hata çıkarabilecek satırı try içine al; devamını else bloğuna taşı.
  • Özel except'i geniş olanın arkasına yazmak: Python bloğu yukarıdan aşağı tarar ve ilk eşleşeni çalıştırır. except Exception önce gelirse ondan sonraki except ValueError hiç çalışmaz. Önce özel türleri, en sonda gerekirse geniş olanı yaz.
  • finally içinde return kullanmak: Bu return, try içindeki dönüş değerinin ve bekleyen hatanın yerine geçebilir; hata sessizce kaybolabilir. finally bloğunu yalnızca temizlik için kullan, değeri blok dışında döndür.
  • finally'de kapatılacak nesneyi tanımlanmadan kullanmak: open() satırı hata verirse dosya değişkeni hiç oluşmaz ve finally içindeki kapat() çağrısı NameError üretir. Değişkeni try'dan önce None ile başlatıp kontrol et ya da with ifadesini kullan.
  • else'i hiç kullanmamak ya da yanlış anlamak: else, hata olduğunda çalışan blok değildir; try hatasız bittiğinde çalışır. Başarı durumuna ait kodu try'ın içine yığmak yerine else'e yaz.

Bu maddeleri kendi kodunda ne kadar yakaladığını görmek istersen ücretsiz Python bilgi testini çözebilirsin. Testteki sorular hangi bilgiyi pekiştirmen gerektiğini fark etmene yardımcı olur.

Sık Sorulan Sorular

try except yazarken else bloğu zorunlu mu?

Hayır. else isteğe bağlıdır. Bir try bloğu için en az bir except ya da finally yeterlidir. else, yalnızca hata çıkmadığında çalışmasını istediğin kodu try'dan ayırmak istediğinde işe yarar.

finally bloğu her durumda çalışır mı?

Hata olsun olmasın, try içinde return bulunsun bulunmasın finally çalışır. Program işletim sistemi düzeyinde aniden sonlandırılırsa ya da süreç öldürülürse çalışma şansı kalmaz; gündelik kodda bu durumu düşünmen gerekmez.

except Exception ile belirli bir hata türünü yakalamak arasında ne fark var?

Belirli tür (örneğin ValueError) yalnızca beklediğin hatayı yakalar, diğer hatalar görünür kalır. except Exception neredeyse tüm hataları yakalar ve gerçek nedeni gizleyebilir. Önce belirli türleri yazmak, geniş yakalamayı yalnızca mesajı yazdırmak ya da kayda almak gibi bilinçli bir amaçla kullanmak daha sağlıklıdır.

else bloğundaki kodu try bloğuna yazsam ne değişir?

Kod aynı sırayla çalışır ama bu kodun içinde çıkan hata da aynı try'ın except bloğuna düşer. Yani beklemediğin bir hata, yanlışlıkla yakalanıp başka bir hatanın mesajıyla karışabilir. else'e yazdığında bu kodun hataları except tarafından yakalanmaz, böylece try yalnızca denediğin riskli satırı korur.

Özetle, try riskli satırı dener, except beklediğin hatayı karşılar, else başarı durumunu ayırır, finally temizliği garanti eder. Karar tablosunu küçük örneklerle kendi dosyanda çalıştırmak, hangi bloğun ne zaman devreye girdiğini en net biçimde gösterir.

Bu içerik aradığın cevabı verdi mi?
Yanıtın, hangi yazıları geliştirmemiz gerektiğini anlamamıza yardımcı olur.
Bu içeriğin üretilmesinde yapay zeka araçlarından destek alınmıştır.

Bu konudan sonra ne okuyabilirsin?

Tüm yazılar

İlgili Eğitimler

Berk Keskin, yazılım geliştirici ve eğitmen
Yazar

Berk Keskin Kimdir?

Yazılıma 12 yaşında başladı; İzmir Ekonomi Üniversitesi'ni bölüm birincisi ve yüksek şeref öğrencisi olarak tamamladı. Bugün yalnızca eğitim vermekle kalmıyor, sektörde aktif olarak yazılım projeleri geliştiriyor ve gerçek dünya deneyimini birebir derslerine taşıyor. Ezberden uzak, mühendislik zihniyetini merkeze alan sürdürülebilir öğrenme sistemleri tasarlayarak sorgulayan, üreten ve problem çözebilen yeni nesil yazılımcılar yetiştiriyor.

Sektörel Deneyim & Projeler

  • Ticarify Entegrasyon Yazılım logosu CEO Ticarify Entegrasyon YazılımPazaryerleri ve e-ticaret sitelerine otomatik e-fatura kesimi, sipariş ve kargo takibi hizmetleri sunan e-Dönüşüm platformunun API mimarisini ve yazılım ekibini yönetmektedir.
  • Benim Düğünüm logosu CEO Benim DüğünümDijital etkinlik ve anı paylaşım platformu.
  • Siberdizayn logosu Yazılım Ekibi Lideri SiberdizaynYüksek anlık oyuncu trafiğine sahip oyun kontrol panelleri ve sunucu altyapıları geliştiren yazılım ekibine liderlik etmektedir.
  • MEDYOGRAFYA 360° Dijital Çözümler logosu Dijital Strateji Lideri MEDYOGRAFYA 360° Dijital ÇözümlerŞirketlerin dijital çözümlerde uzun vadede nasıl ilerlemesi gerektiği ve dijital dönüşüm süreçlerinin yönetilmesine destek olmaktadır.
  • İzmir Ekonomi Üniversitesi logosu Danışma Kurulu Üyesi İzmir Ekonomi ÜniversitesiMezun olduğu üniversitesinde, Bilgisayar Programcılığı bölümünün akademik müfredatını güncel sektör ihtiyaçlarına göre şekillendirmek adına Danışma Kurulu'nda görev almaktadır.
WhatsApp Hemen Ara