Algoritma: Fonksiyonlar
Fonksiyon nedir, bir işi bir kez tanımlayıp adıyla nasıl tekrar tekrar çağırırız? Parametre, DÖNDÜR, kara kutu ve yerel değişkeni kod yazmadan, kalemle öğren.

Seri · Algoritmalar
- 1. Algoritma Nedir? — Yazılıma Sıfırdan Başlangıç
- 2. Algoritma: Akış Şemaları
- 3. Algoritma: Sözde Kod
- 4. Algoritma: Değişkenler
- 5. Algoritma: Koşullar
- 6. Algoritma: Döngüler
- 7. Algoritma: Listeler
- 8. Algoritma: Fonksiyonlar
Önceki yazıda listeleri öğrendik ve güzel bir şey yaptık: bir listenin ortalamasını bulduk — döngüyle gezip topladık, sonra eleman sayısına böldük. Şimdi hayal et: programın bu ortalamayı beş ayrı yerde hesaplasın — bir öğrenci karnesinde, bir sınıf özetinde, bir grafikte. O döngülü bloğu beş kez kopyalayıp yapıştıracak mısın? Ya sonradan bir hata bulursan — hepsini tek tek mi düzelteceksin?
Daha iyi bir yol var: o adım grubuna bir isim ver, bir kez yaz ve gerektiğinde sadece adını söyle. İşte bu adlı, tekrar tekrar kullanılabilen adım grubuna fonksiyon diyoruz. Bu yazının konusu bu: bir işi bir kez tanımlayıp, adıyla dilediğin kadar çağırmak. Fonksiyon, şimdiye kadar öğrendiğimiz her şeyin (değişken, koşul, döngü, liste) üstüne oturan ve programlarımızı ilk kez derli toplu parçalara bölmemizi sağlayan fikir.
Neden fonksiyona ihtiyacımız var?
En baştaki soruna dönelim. Diyelim ki iki ayrı sınıfın not ortalamasını hesaplayıp yazdırmak istiyorsun. Listeler yazısındaki ortalama bloğunu bilerek iki kez yazalım ki sorunu gözünle gör:
# A sınıfıtoplam ← 0i ← 1ZAMAN i ≤ uzunluk(A_notları) DOĞRU İKEN toplam ← toplam + A_notları[i] i ← i + 1DÖNGÜ SONUYAZ toplam / uzunluk(A_notları)
# B sınıfı — birebir aynı adımlar, sadece liste adı değiştitoplam ← 0i ← 1ZAMAN i ≤ uzunluk(B_notları) DOĞRU İKEN toplam ← toplam + B_notları[i] i ← i + 1DÖNGÜ SONUYAZ toplam / uzunluk(B_notları)Aynı sekiz satırı iki kez yazdık — tek fark liste adı. Üç sıkıntı var. Birincisi tekrar: Üçüncü, dördüncü sınıf gelince kod uzadıkça uzar. İkincisi hata riski: Yarın “ortalamayı yanlış hesaplamışım, sıfıra bölünmeyi de kontrol etmeliyim” dersen, bu düzeltmeyi her kopyada ayrı ayrı yapman gerekir; birini unutursan program bir yerde doğru, bir yerde yanlış çalışır. Üçüncüsü okunmazlık: Kodun asıl niyeti (“iki sınıfın ortalamasını al”) bu tekrar eden kalabalığın içinde kayboluyor.
Günlük hayatta bu tuzağa düşmeyiz. Bir yemek tarifinde her seferinde “sosu şöyle hazırla: soğanı doğra, kavur, salçayı ekle…” diye baştan yazmazsın; bir kez “sos” diye tarif eder, sonra “sosu hazırla” dersin. Bir işe bir ad verip o adı kullanmak — fonksiyonun tüm fikri budur.
Fonksiyon nedir?
Bir fonksiyon, bir grup adıma verilmiş bir isimdir. İki ayrı iş yaparsın:
- Tanımlarsın (bir kez): Adımları yazıp onlara bir ad verirsin. Bu, adımları çalıştırmaz — sadece “hazır bekleyen” bir tarif oluşturur.
- Çağırırsın (istediğin kadar): O ismi söylersin ve adımlar tam o an çalışır. Bir kez tanımla, yüz kez çağır.
Bunu somutlaştıralım. En basit fonksiyon, hiçbir bilgi alıp vermeden sadece bir iş yapar. Sözde kodda bir fonksiyonu FONKSIYON ile açar, adımları içeri girintili yazar ve FONKSIYON SONU ile kapatırız — tıpkı koşullardaki BİTİREĞER ya da döngülerdeki DÖNGÜ SONU gibi bir kapanış:
FONKSIYON selamVer YAZ "Merhaba!" YAZ "Bugün nasılsın?"FONKSIYON SONU
selamVer (çağır — iki satır çalışır)selamVer (tekrar çağır — yine çalışır)Dikkat et: FONKSIYON selamVer … FONKSIYON SONU arasını yazmak, ekrana hiçbir şey basmaz. Orası sadece tanım. Ekrana “Merhaba!” yazdıran şey, aşağıdaki selamVer çağrılarıdır. İki kez çağırdık, iki kez selam verdi. Bir kez yazdık, istediğimiz kadar kullandık.
Girdi: fonksiyona bilgi vermek (parametre)
selamVer her seferinde aynı şeyi diyor. Ama çoğu zaman fonksiyonun duruma göre farklı davranmasını isteriz: herkese ismiyle selam versin. Bunun için fonksiyona girdi veririz. Bir meyve sıkacağını düşün: içine ne koyarsan onun suyunu verir. Fonksiyon da böyle — içine bir değer koyarsın, o değerle çalışır.
Fonksiyonun alacağı girdiye, tanımın içinde bir yer tutucu isim veririz; buna parametre denir. Çağırırken o yer tutucunun yerine gerçek bir değer koyarız; buna da argüman denir:
FONKSIYON selamVer(isim) YAZ "Merhaba, " + isim + "!"FONKSIYON SONU
selamVer("Ada") → Merhaba, Ada!selamVer("Can") → Merhaba, Can!Buradaki +, değişkenler yazısından tanıdığın metin birleştirme. Tanımdaki isim bir parametre — boş bir kutu gibi bekliyor. selamVer("Ada") dediğinde "Ada" argümanı o kutuya girer ve fonksiyon isim gördüğü her yerde “Ada”yı kullanır. Bir sonraki çağrıda kutuya “Can” girer. Aynı fonksiyon, farklı girdiyle farklı iş yapar.
Çıktı: fonksiyondan sonuç almak (DÖNDÜR)
Şimdiye kadarki fonksiyonlarımız iş yaptı ama geriye bir sonuç vermedi. Oysa çoğu zaman fonksiyonun bir şey hesaplayıp bize geri vermesini isteriz — bir hesap makinesinin cevabı ekrana verip beklemesi gibi. Bir fonksiyonun sonucu geri vermesine DÖNDÜR diyoruz:
FONKSIYON kare(sayı) DÖNDÜR sayı × sayıFONKSIYON SONU
sonuç ← kare(5) (kare(5), 25'i döndürür; o 25 sonuç'a girer)YAZ sonuç → 25kare(5) çağrısı çalışır, 5 × 5 = 25 hesaplar ve DÖNDÜR ile 25’i çağırana geri verir. O geri verilen 25’i bir değişkene (sonuç) koyabildiğimize dikkat et — işte fonksiyonun gücü burada. Artık kare, sayı üreten bir araç gibi; çıktısını istediğin yere koyabilirsin: YAZ kare(3), alan ← kare(kenar), hatta kare(kare(2)) (2’nin karesinin karesi = 16).
Bir fonksiyon çağrısında olup biteni şöyle canlandırabilirsin: ana program bir an durur, argümanı fonksiyona yollar; fonksiyon işini yapıp sonucu DÖNDÜR ile geri verir; ana program da o sonucu alıp kaldığı yerden devam eder:
flowchart TD
A["Ana program<br/>sonuç ← kare(5)"] -->|"5 gönderilir (argüman)"| B["kare(sayı) fonksiyonu<br/>DÖNDÜR sayı × sayı"]
B -->|"25 geri döner (DÖNDÜR)"| C["Ana program devam eder<br/>sonuç artık 25"]Okun fonksiyona girip bir değerle geri döndüğüne dikkat et — çağrı, programın akışını bir an fonksiyona verir, DÖNDÜR de sonucu alıp geri getirir. Burada, yeni başlayanların en sık karıştırdığı noktaya geldik:
Girdi ve çıktı birlikte: gerçek bir fonksiyon
Şimdi parçaları birleştirip yazının başındaki sorunu çözelim. Listelerdeki ortalama bloğunu, bir girdi alan (liste) ve bir çıktı döndüren (ortalama) gerçek bir fonksiyona dönüştürelim:
FONKSIYON ortalama(liste) toplam ← 0 i ← 1 ZAMAN i ≤ uzunluk(liste) DOĞRU İKEN toplam ← toplam + liste[i] i ← i + 1 DÖNGÜ SONU DÖNDÜR toplam / uzunluk(liste)FONKSIYON SONU
YAZ ortalama(A_notları) (A sınıfının ortalaması)YAZ ortalama(B_notları) (B sınıfının ortalaması)YAZ ortalama([100, 90, 80]) (hazır bir listeyle de çağırabilirsin → 90)Bak, yazının başındaki o iki kopyalı, upuzun kod nasıl da eridi: ortalama mantığını bir kez yazdık, sonra üç farklı liste için sadece çağırdık. Yarın “sıfıra bölünmeyi kontrol edeyim” dersen, düzeltmeyi tek bir yerde — fonksiyonun içinde — yaparsın ve bütün çağrılar kendiliğinden düzelir. İşte fonksiyonların vaat ettiği şey buydu.
İçeride, bu seride öğrendiğimiz her şeyin bir arada çalıştığına dikkat et: bir liste parametresi, bir döngü, bir biriktirici (toplam), bir değişken (i) ve sonunda bir DÖNDÜR. Fonksiyon, bütün bu parçaları tek bir adın arkasına saklıyor.
Aslında bir fonksiyonun içi, tıpkı bu seride çizdiğimiz gibi iki ucu belli bir algoritmadır: parametreyle girer, DÖNDÜR ile çıkar. ortalamanın içindeki adımları akış şemasıyla çizersek, döngüler yazısındaki o tanıdık şemanın bir fonksiyonun sınırları içine alınmış hâlini görürüz:
flowchart TD
A(["ortalama(liste) çağrılır"]) --> B["toplam ← 0<br/>i ← 1"]
B --> C{"i ≤ uzunluk(liste) mi?"}
C -- Evet --> D["toplam ← toplam + liste[i]"]
D --> E["i ← i + 1"]
E --> C
C -- Hayır --> F(["DÖNDÜR toplam / uzunluk(liste)"])Baştaki yuvarlak kutu, fonksiyonun çağrıldığı (başladığı) yer; sondaki kutu ise sonucu verip fonksiyondan çıktığı yerdir — DÖNDÜR, bir algoritmanın “Bitti” ucunun fonksiyondaki karşılığıdır. Bir fonksiyon, işte böyle iki ucu belli, adlandırılmış bir algoritmadan başka bir şey değil.
Fonksiyonu bir “kara kutu” gibi düşün
Şimdi fonksiyonların asıl büyüsüne geldik. Yukarıdaki ortalamayı çağırırken, içinde döngü mü var, nasıl topluyor — bunları düşündün mü? Düşünmene gerek yok. ortalama(A_notları) yazdığında, tek bildiğin şu: bir liste veriyorsun, bir ortalama geri alıyorsun. İçerisi senin için bir kara kutu — ne girdiğini ve ne çıktığını bilirsin, içindeki işleyişi bilmen gerekmez.
flowchart LR
A["Girdi (parametre)<br/>liste = [90, 80, 100]"] --> B["ortalama<br/>KARA KUTU<br/>(içi bizi ilgilendirmez)"]
B --> C["Çıktı (DÖNDÜR)<br/>90"]Ortadaki kutunun içinde döngü mü var, başka bir yöntem mi — dışarıdan bakınca hiç fark etmez; sen yalnızca soldaki girdiyi verir, sağdaki çıktıyı alırsın. Bu, hayatının her yerinde yaptığın bir şey:
- Televizyon kumandası: Düğmeye basarsın, kanal değişir. İçindeki kızılötesi sinyali, devreleri bilmene gerek yok.
- Mikrodalga: Yemeği koyar, süreyi girer, başlat dersin. İçeride ne olduğuyla uğraşmazsın.
- Musluk: Açarsın, su gelir. Suyun hangi borulardan, hangi pompayla geldiğini düşünmezsin.
Fonksiyonun içi kendine ait: yerel değişkenler
ortalama fonksiyonunun içinde toplam ve i diye iki değişken kullandık. Peki bu isimler, fonksiyonun dışında da var mı? Hayır. Bir fonksiyonun içinde tanımlanan değişkenler yalnızca orada yaşar; fonksiyon bitince yok olurlar ve dışarıdan görülmezler. Bunlara yerel değişken denir; bir fonksiyonun kendine ait, özel karalama defteri gibidirler.
Bu neden iyi bir şey? Çünkü iki farklı fonksiyon, birbirine hiç karışmadan aynı ismi kullanabilir. ortalamanın içinde bir i var; başka bir fonksiyonun içinde de bir i olabilir; ikisi bambaşka kutulardır, birbirini ezmez. Her fonksiyon kendi köşesinde, kendi değişkenleriyle rahatça çalışır.
Fonksiyon, fonksiyonu çağırır
Fonksiyonların bir güzelliği daha var: bir fonksiyonun içinden başka bir fonksiyonu çağırabilirsin. Küçük parçaları birleştirerek daha büyük işler kurarsın. Örneğin bir öğrencinin notlarından hem ortalamayı hem de “geçti mi?” bilgisini üretelim; ikincisi, ilkini kullansın:
FONKSIYON geçtiMi(liste) ort ← ortalama(liste) (yukarıda tanımladığımız fonksiyonu çağırıyoruz) EĞER ort ≥ 50 İSE DÖNDÜR doğru DEĞİLSE DÖNDÜR yanlış BİTİREĞERFONKSIYON SONU
YAZ geçtiMi([70, 40, 55]) → doğru (ortalama 55, geçti)geçtiMi, ortalamayı kendisi hesaplamıyor — o işi bilen ortalama fonksiyonuna havale ediyor, dönen sonucu bir koşulla değerlendirip doğru/yanlış (boolean) döndürüyor. Küçük, tek işlik parçalardan büyük işler kurmanın yolu budur. Not: geçtiMi gibi, geriye doğru/yanlış döndüren fonksiyonlara bazen “evet/hayır sorusu soran fonksiyon” gözüyle bakabilirsin — çiftMi, boşMu, geçerliMi gibi.
Hazır fonksiyonlar: tekerleği yeniden icat etme
Yukarıdaki ipucunda değindiğimiz gibi, her programlama dili sık gereken işler için önceden yazılmış fonksiyonlarla gelir: ekrana basmak, bir listenin uzunluğunu almak, karekök hesaplamak, bir metni büyük harfe çevirmek… Bunlara hazır (yerleşik) fonksiyonlar, topluca da kütüphane denir. Amaç basit: tekerleği yeniden icat etme. Karekök almak için her seferinde sıfırdan bir algoritma yazmazsın; dilin sana verdiği hazır fonksiyonu çağırır, kendi asıl işine odaklanırsın.
Gerçek programlama, büyük ölçüde budur: bir kısmı senin yazdığın, bir kısmı hazır gelen fonksiyonları isimleriyle birleştirerek, katman katman daha büyük işler kurmak. Her fonksiyon bir tuğla; program, bu tuğlalardan kurduğun bina.
Sık yapılan hatalar
Kendin dene
Kalem ve kâğıt yeter. Her egzersizde önce fonksiyonu tanımla (FONKSIYON … FONKSIYON SONU), sonra onu birkaç farklı argümanla çağırıp kâğıtta sonucu izle. Girdi (parametre) ve çıktı (DÖNDÜR) ayrımını unutma.
Egzersiz 1 — Büyük olanı döndür (kolay)
İki sayı alan ve büyük olanı döndüren bir
buyukOlan(a, b)fonksiyonu yaz. SonrabuyukOlan(3, 9)vebuyukOlan(12, 7)ile çağırıp sonuçlarını yazdır.
Egzersiz 2 — Çift mi? (orta)
Bir sayı alıp, o sayı çiftse
doğru, tekseyanlışdöndüren birçiftMi(sayı)fonksiyonu yaz.çiftMi(4),çiftMi(7)ile dene.
Egzersiz 3 — Listeyi toplayan fonksiyon (orta)
Bir sayı listesi alıp, elemanlarının toplamını döndüren bir
topla(liste)fonksiyonu yaz. Sonra iki farklı listeyle çağır:topla([10, 20, 30])vetopla([5, 5, 5, 5]).
Egzersiz 4 — Karne: fonksiyonları birleştir (mini proje)
ortalama(liste)(yazıdakini kullan) veenYuksek(liste)(en büyük elemanı döndüren) fonksiyonlarını yaz. Sonra birnotlar ← [65, 90, 78, 55]listesi için her ikisini de çağırıp “Ortalama: … , En yüksek: …” biçiminde bir karne yazdır.
Özet
İlgili yazılar
Sıkça sorulan sorular
Fonksiyon nedir?
Fonksiyon, bir grup adıma bir isim verip onları tek bir birim hâline getirmektir: bir kez tanımlarsın, sonra o ismi söyleyerek (çağırarak) istediğin kadar çalıştırırsın. Bir yemek tarifine ad vermek gibi — "sosu hazırla" dersin, bütün adımları tekrar yazmazsın. Aynı işi farklı yerlerde tekrar tekrar kullanmanın ve karmaşık bir programı küçük, adlı parçalara bölmenin yoludur.
Neden fonksiyon kullanırız?
Üç büyük sebep var. Tekrarı önler: aynı adımları kopyalayıp yapıştırmak yerine bir kez yazarsın (bir hata çıkarsa tek yerde düzeltirsin). Karmaşayı böler: uzun bir programı, her biri tek bir işi yapan küçük adlı parçalara ayırırsın. Ve gizler: bir fonksiyonu kullanmak için içinin nasıl çalıştığını bilmen gerekmez, sadece ne verip ne aldığını bilirsin.
Parametre ile argüman arasındaki fark nedir?
Parametre, fonksiyonu tanımlarken kullandığın yer tutucu isimdir (FONKSIYON selamVer(isim) içindeki "isim"). Argüman ise fonksiyonu çağırırken o yer tutucuya koyduğun gerçek değerdir (selamVer("Ada") içindeki "Ada"). Kısaca: parametre tarifte yazan "bir soğan", argüman ise elindeki o soğandır. Fonksiyon her çağrıldığında argüman değişebilir, parametre ismi aynı kalır.
DÖNDÜR (return) ile YAZ (print) arasındaki fark nedir?
YAZ, bir değeri ekrana basar — insan görür ama program onunla bir şey yapamaz. DÖNDÜR ise sonucu çağırana geri verir, böylece o sonucu bir değişkene koyabilir, bir işleme sokabilir ya da başka bir fonksiyona verebilirsin. YAZ göstermek, DÖNDÜR sonucu teslim etmek içindir. Yeni başlayanların en sık karıştırdığı ayrım budur.
Yerel değişken (kapsam / scope) nedir?
Bir fonksiyonun içinde tanımlanan değişken yalnızca orada yaşar; fonksiyon bitince yok olur ve dışarıdan görülmez. Buna yerel değişken denir. Fonksiyonun kendine ait, özel bir karalama defteri gibidir. Bu sayede iki farklı fonksiyon aynı ismi (örneğin i ya da toplam) birbirine karışmadan kullanabilir; her birinin kendi kopyası olur.
Fonksiyonu tanımlamak ile çağırmak farkı nedir?
Tanımlamak, fonksiyonun adımlarını bir kez yazıp ona bir isim vermektir — ama bu, adımları çalıştırmaz, sadece "hazır bekleyen" bir tarif oluşturur. Çağırmak ise o ismi söyleyip adımları o an çalıştırmaktır. Bir fonksiyonu tanımlayıp hiç çağırmazsan hiçbir şey olmaz; tıpkı bir tarifi yazıp hiç pişirmemek gibi.
Hazır (built-in) fonksiyon nedir?
Programlama dilleri, sık gereken işler için önceden yazılmış fonksiyonlarla gelir — sen yazmadan kullanırsın. Bir listenin uzunluğunu veren uzunluk, ekrana basan YAZ, karekök alan gibi işler bunlara örnektir. Bu hazır fonksiyon topluluklarına kütüphane denir. Amaç tekerleği yeniden icat etmemek: temel işleri hazır al, sen kendi asıl işine odaklan.
Fonksiyon neden "kara kutu"ya benzetilir?
Çünkü bir fonksiyonu kullanmak için içinde ne olup bittiğini bilmen gerekmez; sadece ne verdiğini (girdi) ve ne aldığını (çıktı) bilmen yeter. Tıpkı televizyon kumandası ya da mikrodalga gibi: düğmeye basarsın, iş olur, içindeki elektronikle uğraşmazsın. Bu "içeriyi gizleme" fikrine soyutlama denir ve büyük programları yönetilebilir kılan şeydir.