Takip et

JavaScript Dizilerinde Mutator Metotlar: Detaylı Rehber

JavaScript Dizilerinde Mutator Metotlar: Detaylı Rehber JavaScript, web geliştirmeden sunucu tarafı uygulamalara kadar geniş bir yelpaze

JavaScript Dizilerinde Mutator Metotlar: Detaylı Rehber

JavaScript, web geliştirmeden sunucu tarafı uygulamalara kadar geniş bir yelpazede kullanılan dinamik bir dildir. Bu dilin temel veri yapılarından biri olan diziler (Arrays), veri koleksiyonlarını düzenlemek ve yönetmek için vazgeçilmezdir. JavaScript dizileri, bu koleksiyonlar üzerinde çeşitli işlemler yapmamızı sağlayan zengin bir metot setine sahiptir. Bu metotlar iki ana kategoriye ayrılır: mutator (değiştirici) metotlar ve non-mutator (değiştirmeyen) metotlar.

Bu rehberde, orijinal diziyi doğrudan değiştiren “mutator” metotlara odaklanacağız. Bu metotlar, dizinin içeriğini, boyutunu veya elemanlarının sırasını doğrudan manipüle ederek performansı artırabilir veya bellek kullanımını optimize edebilir. Ancak, bu davranışın yan etkileri olabileceği için dikkatli kullanılmaları gerekir. Gelin, bu güçlü metotları ve pratik kullanımlarını derinlemesine inceleyelim.

1. Mutator Metotlara Giriş ve Temel Dizi Manipülasyonları

Mutator metotlar, çağrıldıkları diziyi doğrudan (in-place) değiştirirler. Bu, metodun yeni bir dizi döndürmek yerine, mevcut dizinin kendisini modifiye ettiği anlamına gelir. Bu davranış, özellikle büyük dizilerle çalışırken bellek verimliliği sağlayabilir, ancak dizinin referansını kullanan diğer kod parçalarını da etkileyeceği için dikkatli olunmalıdır.

1.1. Eleman Ekleme ve Çıkarma: push(), pop(), shift(), unshift()

Bu dört metot, dizinin başından veya sonundan eleman eklemek veya çıkarmak için en sık kullanılan mutator metotlardır.

push(): Dizinin Sonuna Eleman Ekleme

push() metodu, bir veya daha fazla elemanı dizinin sonuna ekler ve dizinin yeni uzunluğunu döndürür.


    let meyveler = ["elma", "muz", "çilek"];
    console.log("Orijinal dizi:", meyveler); // ["elma", "muz", "çilek"]

    let yeniUzunluk = meyveler.push("portakal");
    console.log("push sonrası dizi:", meyveler); // ["elma", "muz", "çilek", "portakal"]
    console.log("Yeni uzunluk:", yeniUzunluk); // 4

    meyveler.push("kivi", "üzüm");
    console.log("Birden fazla eleman ekleme sonrası:", meyveler); // ["elma", "muz", "çilek", "portakal", "kivi", "üzüm"]
    

pop(): Dizinin Sonundan Eleman Çıkarma

pop() metodu, dizinin sonundaki elemanı kaldırır ve bu elemanı döndürür. Dizi boşsa undefined döndürür.


    let sayilar = [1, 2, 3, 4, 5];
    console.log("Orijinal dizi:", sayilar); // [1, 2, 3, 4, 5]

    let sonEleman = sayilar.pop();
    console.log("pop sonrası dizi:", sayilar); // [1, 2, 3, 4]
    console.log("Çıkarılan eleman:", sonEleman); // 5

    sayilar.pop(); // Bir eleman daha çıkar
    console.log("İkinci pop sonrası dizi:", sayilar); // [1, 2, 3]
    

shift(): Dizinin Başından Eleman Çıkarma

shift() metodu, dizinin başındaki elemanı kaldırır ve bu elemanı döndürür. Dizi boşsa undefined döndürür. pop()‘un aksine, bu işlem dizideki tüm diğer elemanların indekslerini değiştirdiğinden, büyük dizilerde pop()‘a göre daha yavaş olabilir.


    let ogrenciler = ["Ali", "Ayşe", "Mehmet", "Zeynep"];
    console.log("Orijinal dizi:", ogrenciler); // ["Ali", "Ayşe", "Mehmet", "Zeynep"]

    let ilkOgrenci = ogrenciler.shift();
    console.log("shift sonrası dizi:", ogrenciler); // ["Ayşe", "Mehmet", "Zeynep"]
    console.log("Çıkarılan öğrenci:", ilkOgrenci); // Ali
    

unshift(): Dizinin Başına Eleman Ekleme

unshift() metodu, bir veya daha fazla elemanı dizinin başına ekler ve dizinin yeni uzunluğunu döndürür. shift() gibi, bu işlem de tüm mevcut elemanların indekslerini değiştirdiği için büyük dizilerde push()‘a göre daha yavaş olabilir.


    let renkler = ["kırmızı", "mavi"];
    console.log("Orijinal dizi:", renkler); // ["kırmızı", "mavi"]

    let yeniUzunlukRenk = renkler.unshift("yeşil");
    console.log("unshift sonrası dizi:", renkler); // ["yeşil", "kırmızı", "mavi"]
    console.log("Yeni uzunluk:", yeniUzunlukRenk); // 3

    renkler.unshift("sarı", "mor");
    console.log("Birden fazla eleman ekleme sonrası:", renkler); // ["sarı", "mor", "yeşil", "kırmızı", "mavi"]
    

Pratik Bilgi: Performans kritik uygulamalarda, dizinin başından eleman ekleme/çıkarma (shift()/unshift()) yerine, dizinin sonundan eleman ekleme/çıkarma (push()/pop()) tercih etmek genellikle daha verimlidir. Çünkü shift() ve unshift(), dizideki her elemanın indeksini yeniden hesaplamayı gerektirirken, push() ve pop() sadece dizinin sonunu etkiler.

2. Esnek Değişiklikler İçin splice() Metodu

splice() metodu, JavaScript’teki en güçlü ve çok yönlü mutator metotlardan biridir. Dizinin herhangi bir yerinden eleman eklemenize, silmenize veya mevcut elemanları değiştirmenize olanak tanır. Silinen elemanları içeren bir dizi döndürür.

Sözdizimi: array.splice(başlangıçIndeksi, silinecekElemanSayısı, eklenecekEleman1, ...)

  • başlangıçIndeksi: İşlemin başlayacağı indeks. Negatif bir değer, dizinin sonundan itibaren sayar.
  • silinecekElemanSayısı: başlangıçIndeksi‘nden itibaren kaç elemanın silineceğini belirtir. 0 ise hiçbir eleman silinmez.
  • eklenecekEleman1, ...: İsteğe bağlı olarak, silinen elemanların yerine eklenecek elemanlar.

Örnekler:


    let urunler = ["laptop", "telefon", "tablet", "mouse", "klavye"];
    console.log("Orijinal ürünler:", urunler);

    // 1. Eleman silme: 2. indeksten başlayarak 1 eleman sil
    let silinenTablet = urunler.splice(2, 1);
    console.log("Tablet silme sonrası:", urunler); // ["laptop", "telefon", "mouse", "klavye"]
    console.log("Silinen eleman:", silinenTablet); // ["tablet"]

    // 2. Eleman ekleme: 1. indekse "kulaklık" ekle, hiçbir şey silme
    urunler.splice(1, 0, "kulaklık");
    console.log("Kulaklık ekleme sonrası:", urunler); // ["laptop", "kulaklık", "telefon", "mouse", "klavye"]

    // 3. Eleman değiştirme: 3. indeksten başlayarak 1 elemanı sil ve yerine "webcam" ekle
    let silinenMouse = urunler.splice(3, 1, "webcam");
    console.log("Mouse yerine webcam:", urunler); // ["laptop", "kulaklık", "telefon", "webcam", "klavye"]
    console.log("Silinen eleman:", silinenMouse); // ["mouse"]

    // 4. Sondan sayma: Sondan 2. elemanı sil ("klavye")
    urunler.splice(-1, 1);
    console.log("Sondan eleman silme:", urunler); // ["laptop", "kulaklık", "telefon", "webcam"]
    

Pratik Bilgi: splice() metodu, bir dizinin belirli bir bölümünü tamamen değiştirmek, araya eleman sokmak veya belirli elemanları kaldırmak gibi karmaşık dizi manipülasyonları için vazgeçilmezdir. Özellikle bir “CRUD” (Oluşturma, Okuma, Güncelleme, Silme) uygulamasında bir listedeki öğeleri yönetirken çok işe yarar.

3. Sıralama ve Ters Çevirme Metotları: sort() ve reverse()

Bu metotlar, dizinin elemanlarının sırasını doğrudan değiştirir.

3.1. reverse(): Diziyi Ters Çevirme

reverse() metodu, bir dizinin elemanlarının sırasını tersine çevirir. İlk eleman son, son eleman ilk olur.


    let alfabe = ["a", "b", "c", "d"];
    console.log("Orijinal alfabe:", alfabe); // ["a", "b", "c", "d"]

    alfabe.reverse();
    console.log("Ters çevrilmiş alfabe:", alfabe); // ["d", "c", "b", "a"]

    let sayilarTers = [1, 2, 3, 4, 5];
    sayilarTers.reverse();
    console.log("Sayılar ters çevrilmiş:", sayilarTers); // [5, 4, 3, 2, 1]
    

3.2. sort(): Diziyi Sıralama

sort() metodu, bir dizinin elemanlarını yerinde sıralar ve sıralanmış diziyi döndürür. Varsayılan olarak, elemanlar string’e dönüştürülür ve Unicode kod noktalarına göre alfabetik olarak sıralanır.

Varsayılan Sıralama (String Karşılaştırma)


    let kelimeler = ["elma", "muz", "çilek", "portakal"];
    kelimeler.sort();
    console.log("Alfabetik sıralama:", kelimeler); // ["çilek", "elma", "muz", "portakal"]

    let karisikSayilar = [1, 10, 2, 20, 3];
    karisikSayilar.sort();
    // DİKKAT: Sayısal olarak değil, string olarak sıralar! "10" "2"den önce gelir.
    console.log("Yanlış sayısal sıralama (varsayılan):", karisikSayilar); // [1, 10, 2, 20, 3]
    

Özel Karşılaştırma Fonksiyonu Kullanımı

Sayıları veya nesneleri doğru bir şekilde sıralamak için sort() metoduna bir karşılaştırma fonksiyonu geçirmelisiniz. Bu fonksiyon, iki argüman (a ve b) alır ve şu değerleri döndürmelidir:

  • Negatif bir değer: a, b‘den önce gelir.
  • Pozitif bir değer: a, b‘den sonra gelir.
  • 0: a ve b eşittir, sıralama değişmez.

    let sayilarDuzgun = [1, 10, 2, 20, 3];

    // Artan sırada sıralama (küçükten büyüğe)
    sayilarDuzgun.sort((a, b) => a - b);
    console.log("Doğru sayısal artan sıralama:", sayilarDuzgun); // [1, 2, 3, 10, 20]

    // Azalan sırada sıralama (büyükten küçüğe)
    sayilarDuzgun.sort((a, b) => b - a);
    console.log("Doğru sayısal azalan sıralama:", sayilarDuzgun); // [20, 10, 3, 2, 1]

    // Nesneleri sıralama (örneğin, yaşa göre)
    let kisiler = [
        { ad: "Ali", yas: 30 },
        { ad: "Ayşe", yas: 25 },
        { ad: "Mehmet", yas: 35 }
    ];

    kisiler.sort((a, b) => a.yas - b.yas); // Yaşa göre artan sıralama
    console.log("Yaşa göre sıralanmış kişiler:", kisiler);
    /*
    [
      { ad: 'Ayşe', yas: 25 },
      { ad: 'Ali', yas: 30 },
      { ad: 'Mehmet', yas: 35 }
    ]
    */
    

Pratik Bilgi: Sayısal dizileri sıralarken her zaman bir karşılaştırma fonksiyonu kullanın. Aksi takdirde, sort()‘un varsayılan davranışı beklenmedik sonuçlar verecektir. Nesnelerle çalışırken de hangi özelliğe göre sıralama yapacağınızı karşılaştırma fonksiyonunda belirtmeniz gerekir.

4. Diğer Faydalı Mutator Metotlar: fill() ve copyWithin()

Bu metotlar, belirli senaryolarda oldukça kullanışlı olan daha özel mutator işlemler sunar.

4.1. fill(): Diziyi Belirli Bir Değerle Doldurma

fill() metodu, bir dizinin elemanlarını belirtilen bir değerle değiştirir. İsteğe bağlı olarak bir başlangıç ve bitiş indeksi belirterek dizinin yalnızca bir kısmını doldurabilirsiniz.

Sözdizimi: array.fill(değer, başlangıçIndeksi, bitişIndeksi)


    let bosDizi = new Array(5); // [undefined, undefined, undefined, undefined, undefined]
    bosDizi.fill(0);
    console.log("Sıfırlarla doldurulmuş dizi:", bosDizi); // [0, 0, 0, 0, 0]

    let mektupNotlari = ["A", "B", "C", "D", "F"];
    mektupNotlari.fill("P", 2, 4); // 2. indeksten (dahil) 4. indekse (hariç) kadar doldur
    console.log("Kısmi doldurma:", mektupNotlari); // ["A", "B", "P", "P", "F"]

    mektupNotlari.fill("X", 1); // 1. indeksten sonuna kadar doldur
    console.log("Kısmi doldurma (baştan sona):", mektupNotlari); // ["A", "X", "X", "X", "X"]
    

4.2. copyWithin(): Dizinin Elemanlarını Kendi İçinde Kopyalama

copyWithin() metodu, dizinin bir kısmını kendi içinde başka bir konuma kopyalar ve orijinal diziyi değiştirir. Dizinin uzunluğunu değiştirmez.

Sözdizimi: array.copyWithin(hedefIndeks, başlangıçIndeksi, bitişIndeksi)

  • hedefIndeks: Kopyalanan elemanların yapıştırılacağı sıfır tabanlı indeks.
  • başlangıçIndeksi: Kopyalamanın başlayacağı sıfır tabanlı indeks.
  • bitişIndeksi: Kopyalamanın biteceği sıfır tabanlı indeks (hariç).

    let numaralar = [1, 2, 3, 4, 5, 6, 7];
    console.log("Orijinal numaralar:", numaralar);

    // 0. indeksten başlayarak 3. indeksten 5. indekse kadar olan elemanları kopyala
    // Yani [4, 5] elemanlarını kopyala ve 0. indekse yapıştır
    numaralar.copyWithin(0, 3, 5);
    console.log("copyWithin (0, 3, 5):", numaralar); // [4, 5, 3, 4, 5, 6, 7]

    let harfler = ["a", "b", "c", "d", "e"];
    // 2. indeksten başlayarak 0. indeksten 2. indekse kadar olan elemanları kopyala
    // Yani ["a", "b"] elemanlarını kopyala ve 2. indekse yapıştır
    harfler.copyWithin(2, 0, 2);
    console.log("copyWithin (2, 0, 2):", harfler); // ["a", "b", "a", "b", "e"]
    

Pratik Bilgi: fill() ve copyWithin(), özellikle belirli bir aralığı hızlıca doldurmanız veya dizinin içinde veri bloklarını taşımanız gerektiğinde kullanışlıdır. Örneğin, bir oyun tahtasını sıfırlamak veya bir veri arabelleğini yönetmek gibi durumlarda faydalı olabilirler.

Sonuç ve Sıkça Sorulan Sorular (SSS)

JavaScript’teki mutator metotlar, dizileri verimli bir şekilde değiştirmek için güçlü araçlardır. Orijinal diziyi doğrudan manipüle etmeleri, performans avantajları sağlarken, kodunuzun öngörülebilirliğini etkileyebileceği için dikkatli kullanım gerektirir. Hangi metodu ne zaman kullanacağınızı bilmek, daha temiz, daha verimli ve daha güvenilir JavaScript kodu yazmanıza yardımcı olacaktır.

Bu rehberde ele aldığımız metotları özetleyecek olursak:

  • push(), pop(), shift(), unshift(): Dizinin başından veya sonundan eleman ekleme/çıkarma.
  • splice(): Dizinin herhangi bir yerinden eleman ekleme, silme veya değiştirme.
  • reverse(): Dizinin elemanlarının sırasını tersine çevirme.
  • sort(): Dizinin elemanlarını sıralama (genellikle özel bir karşılaştırma fonksiyonu ile).
  • fill(): Dizinin elemanlarını belirli bir değerle doldurma.
  • copyWithin(): Dizinin bir kısmını kendi içinde başka bir konuma kopyalama.

Bu metotlar, günlük programlama görevlerinizde size büyük kolaylık sağlayacaktır.

Sıkça Sorulan Sorular (SSS)

1. Mutator metotları kullanmak ne zaman iyidir?

Mutator metotları, özellikle performansın önemli olduğu veya dizinin değiştirilmesinin beklenen davranış olduğu durumlarda kullanmak iyidir. Örneğin, bir kullanıcının sepetine ürün eklemek veya bir listeden öğe kaldırmak gibi durumlarda, orijinal diziyi doğrudan değiştirmek mantıklı olabilir. Ayrıca, bellek kullanımını minimize etmek istediğiniz büyük dizilerle çalışırken de avantajlıdırlar çünkü yeni bir dizi oluşturmazlar.

2. Mutator metotları kullanmaktan ne zaman kaçınmalıyız?

Mutator metotlardan, özellikle uygulamanızın durum yönetiminde (state management) “değişmezlik” (immutability) prensibini benimsediği durumlarda kaçınmalısınız. React, Redux gibi kütüphanelerle çalışırken veya verinin beklenmedik şekilde değişmesini istemediğiniz karmaşık uygulamalarda, orijinal diziyi değiştirmeyen (non-mutator) metotları (örneğin concat(), slice(), map(), filter(), reduce()) tercih etmelisiniz. Bu, hata ayıklamayı kolaylaştırır ve uygulamanın durumunun daha öngörülebilir olmasını sağlar.

3. Bir metodun mutator olup olmadığını nasıl anlarım?

Bir metodun mutator olup olmadığını anlamanın birkaç yolu vardır:

  • Dokümantasyon: MDN Web Docs gibi güvenilir kaynaklar, her metodun “mutates the array” veya “returns a new array” gibi ifadelerle davranışını açıkça belirtir.
  • Dönüş Değeri: Çoğu mutator metot (pop(), shift() hariç) dizinin yeni uzunluğunu veya dizinin kendisini (referansını) döndürür. Non-mutator metotlar ise genellikle yeni bir dizi döndürür.
  • Deneme: Emin değilseniz, küçük bir dizi üzerinde metodu çağırın ve metot çağrısından sonra orijinal diziyi kontrol edin.
  • Metot Adı: Bazı metot adları (örneğin push, pop, sort, reverse) genellikle bir değişiklik ima ederken, concat, slice gibi metotlar yeni bir kopya oluşturmayı düşündürür.

4. Mutator metotlar performans açısından nasıldır?

Genel olarak, mutator metotlar, yeni bir dizi oluşturmadıkları için bellek açısından daha verimlidir. Ancak, performansları metodun kendisine ve dizinin boyutuna bağlıdır:

  • push() ve pop() genellikle çok hızlıdırlar (O(1) zaman karmaşıklığı).
  • shift() ve unshift(), dizinin tüm elemanlarının indekslerini değiştirmeyi gerektirdiği için büyük dizilerde pahalı olabilir (O(n) zaman karmaşıklığı).
  • splice(), sort(), fill() ve copyWithin() gibi metotlar da dizinin boyutuna ve yapılan işleme bağlı olarak O(n) veya O(n log n) gibi zaman karmaşıklıklarına sahip olabilirler.

Performans kritik uygulamalarda, özellikle büyük veri setleriyle çalışırken, bu farklılıkları göz önünde bulundurmak önemlidir.

Yorumlar
İçeriği beğendiniz mi? Bir tartışma başlatın veya görüşlerinizi paylaşın.
Yorum Yaz

Bir yanıt yazın

E-posta adresiniz yayınlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir

E-posta Bülteni
Yazılım Topluluğuna Katılın
En son güncellemeleri, yaratıcı ipuçlarını ve özel kaynakları doğrudan e-posta kutunuza alın. Tasarım ve inovasyonun geleceğini birlikte keşfedelim.