Fonksiyonlar Nedir?
Fonksiyonlar, belirli bir görevi yerine getiren, yeniden kullanılabilir kod bloklarıdır. JavaScript’te fonksiyonlar “birinci sınıf vatandaş” olarak kabul edilir, yani değişkenlere atanabilir, başka fonksiyonlara parametre olarak geçilebilir ve fonksiyonlardan döndürülebilir.
Neden Fonksiyon Kullanırız?
- Kod Tekrarını Önler: Aynı işlemi birden fazla yerde yapabiliriz
- Modülerlik: Kodu küçük, yönetilebilir parçalara böler
- Okunabilirlik: Kodun ne yaptığı daha açık olur
- Test Edilebilirlik: Her fonksiyon ayrı ayrı test edilebilir
- Hata Ayıklama: Problemleri daha kolay buluruz
Fonksiyon Tanımlama Yöntemleri
1. Function Declaration (Fonksiyon Bildirimi)
function selamla(isim) {
return `Merhaba ${isim}!`;
}
// Kullanım
console.log(selamla('Furkan')); // "Merhaba Furkan!"
// Hoisting - tanımlamadan önce çağırılabilir
console.log(erkenSelamla('Test')); // Çalışır!
function erkenSelamla(isim) {
return `Erken merhaba ${isim}!`;
}
2. Function Expression (Fonksiyon İfadesi)
// Anonim fonksiyon
let carpma = function(a, b) {
return a * b;
};
// İsimli fonksiyon ifadesi
let bolme = function bolmeIslemi(a, b) {
if (b === 0) {
console.log('Sıfıra bölünemez!');
return null;
}
return a / b;
};
console.log(carpma(5, 3)); // 15
console.log(bolme(10, 2)); // 5
3. Arrow Functions (Ok Fonksiyonları) - ES6+
// Temel arrow function
let topla = (a, b) => {
return a + b;
};
// Tek ifade için kısa yazım
let kare = x => x * x;
let selamVer = () => 'Merhaba Dünya!';
// Parametre sayısına göre
let tekParam = x => x * 2; // Tek parametre, parantez opsiyonel
let cokParam = (x, y, z) => x + y + z; // Çok parametre, parantez gerekli
let paramYok = () => Math.random(); // Parametre yok, parantez gerekli
console.log(kare(5)); // 25
console.log(tekParam(10)); // 20
console.log(cokParam(1, 2, 3)); // 6
Ipucu
Arrow Function Avantajları: Daha kısa yazım, lexical this binding (gelişmiş konularda önemli). Callback fonksiyonlarda çok kullanışlı!
Parametreler ve Argumentlar
Temel Parametre Kullanımı
function kullaniciBilgisi(isim, yas, sehir) {
console.log(`İsim: ${isim}`);
console.log(`Yaş: ${yas}`);
console.log(`Şehir: ${sehir}`);
}
kullaniciBilgisi('Furkan', 25, 'İstanbul');
// Eksik parametre - undefined olur
kullaniciBilgisi('Ahmet', 30); // sehir = undefined
Varsayılan Parametreler (ES6+)
function selamla(isim = 'Misafir', dil = 'tr') {
const mesajlar = {
tr: `Merhaba ${isim}!`,
en: `Hello ${isim}!`,
fr: `Bonjour ${isim}!`
};
return mesajlar[dil] || mesajlar.tr;
}
console.log(selamla()); // "Merhaba Misafir!"
console.log(selamla('Furkan')); // "Merhaba Furkan!"
console.log(selamla('John', 'en')); // "Hello John!"
Rest Parameters (Kalan Parametreler)
function topla(...sayilar) {
let toplam = 0;
for (let sayi of sayilar) {
toplam += sayi;
}
return toplam;
}
console.log(topla(1, 2, 3)); // 6
console.log(topla(1, 2, 3, 4, 5)); // 15
console.log(topla(10)); // 10
// İlk parametre ayrı, geri kalanı dizi
function ilkVeGeriKalan(ilk, ...geriKalan) {
console.log('İlk:', ilk);
console.log('Geri kalan:', geriKalan);
}
ilkVeGeriKalan('a', 'b', 'c', 'd');
// İlk: a
// Geri kalan: ['b', 'c', 'd']
Destructuring ile Parametreler
// Obje destructuring
function kullaniciOlustur({isim, yas, email, sehir = 'Belirtilmemiş'}) {
return {
id: Date.now(),
isim,
yas,
email,
sehir,
olusturulma: new Date()
};
}
let yeniKullanici = kullaniciOlustur({
isim: 'Furkan',
yas: 25,
email: '[email protected]'
});
console.log(yeniKullanici);
// Dizi destructuring
function koordinatIslemi([x, y, z = 0]) {
return {
x: x,
y: y,
z: z,
mesafe: Math.sqrt(x*x + y*y + z*z)
};
}
console.log(koordinatIslemi([3, 4])); // z = 0
console.log(koordinatIslemi([3, 4, 5])); // z = 5
Return (Geri Dönüş) Değerleri
Temel Return Kullanımı
function dikdortgenAlan(uzunluk, genislik) {
return uzunluk * genislik;
}
function cemberAlan(yaricap) {
return Math.PI * yaricap * yaricap;
}
let alan1 = dikdortgenAlan(5, 3); // 15
let alan2 = cemberAlan(4); // ~50.27
// Return yoksa undefined döner
function mesajYazdir(mesaj) {
console.log(mesaj);
// return yok
}
let sonuc = mesajYazdir('Test'); // undefined
Çoklu Return Değerleri
// Obje döndürme
function islemler(a, b) {
return {
toplam: a + b,
fark: a - b,
carpim: a * b,
bolum: b !== 0 ? a / b : null
};
}
let sonuclar = islemler(10, 5);
console.log(sonuclar); // {toplam: 15, fark: 5, carpim: 50, bolum: 2}
// Dizi döndürme
function minMax(sayilar) {
return [Math.min(...sayilar), Math.max(...sayilar)];
}
let [minimum, maksimum] = minMax([3, 1, 9, 2, 8]);
console.log(`Min: ${minimum}, Max: ${maksimum}`); // Min: 1, Max: 9
Erken Return (Guard Clauses)
function yasiKategoriAl(yas) {
// Geçersiz girdi kontrolü
if (typeof yas !== 'number' || yas < 0) {
return 'Geçersiz yaş';
}
// Erken return'ler - temiz kod
if (yas < 13) return 'Çocuk';
if (yas < 18) return 'Genç';
if (yas < 65) return 'Yetişkin';
return 'Yaşlı';
}
console.log(yasiKategoriAl(25)); // "Yetişkin"
console.log(yasiKategoriAl(-5)); // "Geçersiz yaş"
Scope (Kapsam) Kavramı
Global Scope
// Global değişken - her yerden erişilebilir
let globalDegisken = 'Ben globalim';
function test1() {
console.log(globalDegisken); // Erişebilir
}
function test2() {
globalDegisken = 'Değiştirildi'; // Değiştirilebilir
}
test1(); // "Ben globalim"
test2();
test1(); // "Değiştirildi"
Function Scope
function fonksiyonKapsami() {
let lokalDegisken = 'Ben lokali̧m';
var eskiDeğisken = 'Ben varım';
console.log(lokalDegisken); // Çalışır
if (true) {
let blokDegisken = 'Ben blok içindeyim';
var fonksiyonGeneli = 'Ben fonksiyon genelindeyim';
console.log(blokDegisken); // Çalışır
}
// console.log(blokDegisken); // Hata! Tanımsız
console.log(fonksiyonGeneli); // Çalışır (var hoisting)
}
// console.log(lokalDegisken); // Hata! Fonksiyon dışından erişilemez
Lexical Scope (Sözcüksel Kapsam)
let disaridaki = 'dışarıdaki değer';
function disFonksiyon() {
let disDegisken = 'dış fonksiyon değişkeni';
function icFonksiyon() {
let icDegisken = 'iç fonksiyon değişkeni';
// İç fonksiyon tüm dış kapsamlara erişebilir
console.log(icDegisken); // ✅ Erişebilir
console.log(disDegisken); // ✅ Erişebilir
console.log(disaridaki); // ✅ Erişebilir
}
icFonksiyon();
// console.log(icDegisken); // ❌ Erişemez
}
disFonksiyon();
Closure (Kapanış)
// Basit closure örneği
function disFonksiyon(x) {
// Bu değişken closure ile korunur
return function icFonksiyon(y) {
return x + y; // x'e hala erişebiliyor
};
}
let topla5 = disFonksiyon(5);
console.log(topla5(3)); // 8 (5 + 3)
// Pratik closure örneği - Sayaç
function sayacOlustur() {
let sayac = 0;
return {
artir: function() {
sayac++;
return sayac;
},
azalt: function() {
sayac--;
return sayac;
},
deger: function() {
return sayac;
}
};
}
let benimSayacim = sayacOlustur();
console.log(benimSayacim.artir()); // 1
console.log(benimSayacim.artir()); // 2
console.log(benimSayacim.azalt()); // 1
console.log(benimSayacim.deger()); // 1
// Farklı sayaç
let baskaasayac = sayacOlustur();
console.log(baskaasayac.artir()); // 1 (bağımsız)
Higher-Order Functions (Yüksek Dereceli Fonksiyonlar)
Fonksiyon Parametre Olarak
function islemYap(a, b, islem) {
return islem(a, b);
}
function topla(x, y) { return x + y; }
function carp(x, y) { return x * y; }
console.log(islemYap(5, 3, topla)); // 8
console.log(islemYap(5, 3, carp)); // 15
// Anonim fonksiyon ile
console.log(islemYap(10, 2, function(a, b) {
return a / b;
})); // 5
// Arrow function ile
console.log(islemYap(8, 3, (a, b) => a % b)); // 2
Fonksiyon Döndüren Fonksiyonlar
function carpanOlustur(carpan) {
return function(sayi) {
return sayi * carpan;
};
}
let ikiKati = carpanOlustur(2);
let ucKati = carpanOlustur(3);
console.log(ikiKati(5)); // 10
console.log(ucKati(4)); // 12
// Daha karmaşık örnek
function filtreOlustur(kriter) {
return function(dizi) {
return dizi.filter(kriter);
};
}
let ciftFiltralayici = filtreOlustur(x => x % 2 === 0);
let buyukFiltralayici = filtreOlustur(x => x > 10);
let sayilar = [1, 2, 3, 4, 15, 20, 25];
console.log(ciftFiltralayici(sayilar)); // [2, 4, 20]
console.log(buyukFiltralayici(sayilar)); // [15, 20, 25]
Pratik Örnekler
Kişi Yönetim Sistemi
// Kişi oluşturucu fonksiyon
function kisiOlustur(isim, soyisim, yas, email) {
return {
isim,
soyisim,
yas,
email,
tamIsim: function() {
return `${this.isim} ${this.soyisim}`;
},
yasKategorisi: function() {
if (this.yas < 18) return 'Çocuk';
if (this.yas < 65) return 'Yetişkin';
return 'Yaşlı';
},
emailGecerli: function() {
return this.email.includes('@') && this.email.includes('.');
}
};
}
// Kişi listesi yöneticisi
function kisiListesiOlustur() {
let kisiler = [];
return {
ekle: function(kisi) {
if (kisi.emailGecerli()) {
kisiler.push(kisi);
return true;
}
return false;
},
listele: function() {
return kisiler.map(kisi => ({
tamIsim: kisi.tamIsim(),
yas: kisi.yas,
kategori: kisi.yasKategorisi(),
email: kisi.email
}));
},
ara: function(arama) {
return kisiler.filter(kisi =>
kisi.tamIsim().toLowerCase().includes(arama.toLowerCase())
);
},
yasinaGore: function(minYas, maxYas) {
return kisiler.filter(kisi =>
kisi.yas >= minYas && kisi.yas <= maxYas
);
}
};
}
// Kullanım
let kisiListesi = kisiListesiOlustur();
let furkan = kisiOlustur('Furkan', 'Çelik', 25, '[email protected]');
let ahmet = kisiOlustur('Ahmet', 'Yılmaz', 30, '[email protected]');
kisiListesi.ekle(furkan);
kisiListesi.ekle(ahmet);
console.log(kisiListesi.listele());
console.log(kisiListesi.ara('Furkan'));
Hesap Makinesi Sistemi
function hesapMakinesiOlustur() {
let gecmis = [];
function islemKaydet(islem, sonuc) {
gecmis.push({
islem,
sonuc,
tarih: new Date().toLocaleString('tr-TR')
});
}
return {
topla: function(a, b) {
let sonuc = a + b;
islemKaydet(`${a} + ${b}`, sonuc);
return sonuc;
},
cikar: function(a, b) {
let sonuc = a - b;
islemKaydet(`${a} - ${b}`, sonuc);
return sonuc;
},
carp: function(a, b) {
let sonuc = a * b;
islemKaydet(`${a} × ${b}`, sonuc);
return sonuc;
},
bol: function(a, b) {
if (b === 0) {
let hata = 'Sıfıra bölünemez!';
islemKaydet(`${a} ÷ ${b}`, hata);
return hata;
}
let sonuc = a / b;
islemKaydet(`${a} ÷ ${b}`, sonuc);
return sonuc;
},
us: function(taban, us) {
let sonuc = Math.pow(taban, us);
islemKaydet(`${taban}^${us}`, sonuc);
return sonuc;
},
gecmisGoster: function() {
console.log('İşlem Geçmişi:');
console.log('='.repeat(40));
gecmis.forEach((kayit, indeks) => {
console.log(`${indeks + 1}. ${kayit.islem} = ${kayit.sonuc} (${kayit.tarih})`);
});
},
gecmisTemizle: function() {
gecmis = [];
console.log('Geçmiş temizlendi.');
}
};
}
// Kullanım
let calc = hesapMakinesiOlustur();
console.log(calc.topla(5, 3)); // 8
console.log(calc.carp(4, 7)); // 28
console.log(calc.bol(10, 0)); // Sıfıra bölünemez!
console.log(calc.us(2, 3)); // 8
calc.gecmisGoster();
Pratik Egzersizler
Egzersiz 1: Öğrenci Not Sistemi
function ogrenciSistemiOlustur() {
// 1. Öğrenci ekleme fonksiyonu
// 2. Not ekleme fonksiyonu
// 3. Ortalama hesaplama
// 4. Harf notu belirleme
// 5. Sınıf raporu oluşturma
// Bu sistemi tamamlayın
}
Egzersiz 2: Basit Banka Sistemi
function bankaHesabi(baslangicBakiye = 0) {
// 1. Para yatırma (yatir)
// 2. Para çekme (cek)
// 3. Bakiye sorgulama (bakiye)
// 4. İşlem geçmişi (gecmis)
// 5. Faiz hesaplama (faizHesapla)
// Closure kullanarak güvenli bir sistem oluşturun
}
Egzersiz 3: Görev Yöneticisi
function gorevYoneticisiOlustur() {
// 1. Görev ekleme (ekle)
// 2. Görev tamamlama (tamamla)
// 3. Görev silme (sil)
// 4. Filtreleme (tamamlananlar, bekleyenler)
// 5. Öncelik sıralaması
// Her görev: {id, baslik, aciklama, tamamlandi, oncelik, tarih}
}
Uyarı
Önemli Not: Arrow function’lar kendi this
bağlamına sahip değildir. Obje metodları için function declaration kullanmayı tercih edin veya arrow function’ların this davranışını öğrenin.
Sıradaki Bölüm
Bir sonraki bölümde DOM Manipülasyonu öğreneceksiniz. JavaScript’le HTML elementlerini nasıl seçeceğinizi, değiştireceğinizi ve dinamik web sayfaları oluşturacağınızı keşfedeceksiniz.
Öğrendikleriniz:
- ✅ Function declaration, expression ve arrow function’ları
- ✅ Parametreler, default values ve rest parameters
- ✅ Return değerleri ve çoklu return teknikleri
- ✅ Scope, closure ve lexical scoping kavramları
- ✅ Higher-order functions ve callback’ler
- ✅ Pratik fonksiyon tasarım prensipleri
Artık JavaScript’te kodunuzu düzenli, yeniden kullanılabilir fonksiyonlara ayırabiliyorsunuz! Sırada bu fonksiyonları kullanarak web sayfalarını dinamik hale getirmeyi öğrenmek var. 🎯