- Broadcasting neyi çözer?
- Kuralı doğru okumak: sondan başa şekil karşılaştırması
- newaxis ile boyut eklemek: dış işlemler
- Döngüyü vektörel işleme çevirme kalıpları
- Pratik örnek: tüm noktalar arası mesafeyi döngüsüz hesaplamak
- Sık hatalar ve ayıklama
- Bu beceriyi Mindset programlarında nerede çalışırsınız?
- Sık sorulan sorular
Döngüyü bırakın: NumPy'de broadcasting ve vektörel hesaplama
NumPy broadcasting kurallarını, newaxis ile boyut eklemeyi ve for döngüsünü vektörel işlemlerle değiştirmeyi örneklerle ve sık hatalarla öğrenin.
Broadcasting neyi çözer?
Diziler aynı şekle sahip değilse, NumPy yine de işlemi yapmaya çalışır. Küçük diziyi büyük dizinin şekline "yayarak" elemanlar arası işlemi mümkün kılar. Buna broadcasting (yayın) denir. Asıl kazanç, yayılan dizinin belleğe gerçekten kopyalanmaması ve işlemin döngü yazmadan, C hızında yürümesidir.
En basit örnek bir diziyi bir sayıyla çarpmaktır: a * 10 ifadesinde 10 skalerdir ve her elemana uygulanır. Biraz daha ileri örnek, bir tablonun her satırına aynı vektörü eklemektir. Satış verisinde, her ürünün aylık satış satırından ürün ortalamasını çıkarmak, bir sütun vektörünü tüm sütunlara uygulamak gibi işler hep broadcasting'dir.
Bir vektörel işlemle broadcasting ilişkisi şöyle özetlenir: Vektörel işlem, "bütün diziye aynı anda uygula" fikridir. Broadcasting ise farklı şekilli dizileri bu işleme sokabilmek için gereken uyum kuralıdır. İkisi birlikte, for döngüsünü büyük ölçüde ortadan kaldırır.
Kuralı doğru okumak: sondan başa şekil karşılaştırması
NumPy belgesine göre diziler bir işleme girdiğinde şekiller sondaki (en sağdaki) boyuttan başlayarak sola doğru karşılaştırılır. Karşılaştırılan boyutlar ya birbirine eşit olmalı ya da biri bir olmalıdır. Bu koşulu sağlamayan durumda NumPy "operands could not be broadcast together" hatası verir.
Dizilerin eksen sayısı aynı olmak zorunda değildir. Eksik boyutlar bir sayılır; sonuç, en çok eksene sahip dizinin eksen sayısına ve her konumdaki en büyük boyuta sahip olur. Belgedeki örnekte şekli (5, 1), (1, 6) ve (6,) olan diziler ile bir skaler, ortak olarak (5, 6) şekline yayılabilir.
Uyumlu durumlar için bir ölçü: Sağdan sola her konumda "eşit mi, biri bir mi?" sorusuna evet diyebiliyorsanız dizi uyumludur. Belge şu örnekleri verir: (4, 3) ile (3,) uyumludur ve sonuç (4, 3) olur. (4, 3) ile (4,) ise sondaki boyutlar birbirine eşit olmadığı ve biri bir olmadığı için uyumsuzdur ve hata verir.
a = np.array([[0.0, 0.0, 0.0], [10.0, 10.0, 10.0], [20.0, 20.0, 20.0], [30.0, 30.0, 30.0]]) b = np.array([1.0, 2.0, 3.0]) a + b
Burada b her satıra eklenir. b yerine satır sayısı kadar elemanlı bir dizi verirseniz ValueError alırsınız. Hata iletisi şekilleri yan yana yazar; hata ayıklamanın ilk adımı şekilleri okumaktır.
newaxis ile boyut eklemek: dış işlemler
Bazen tek eksenli dizilerin her elemanını birbiriyle eşlemek istersiniz: her satış temsilcisini her ürünle, her noktayı her noktayla. Bunun için bir diziye boyut ekleyip şekillerin birbirini tamamlamasını sağlarsınız. NumPy belgesinin gösterdiği yol np.newaxis kullanmaktır.
a = np.array([0.0, 10.0, 20.0, 30.0]) b = np.array([1.0, 2.0, 3.0]) a[:, np.newaxis] + b
a[:, np.newaxis] ifadesi (4,) şekilli diziyi (4, 1) şekline getirir. (4, 1) ile (3,) birleşince sonuç (4, 3) olur ve girdilerin tüm olası toplamları bir tabloya dizilir. Belgeye göre sonuç, girdilerin hiçbirinden daha büyük bir çıktıdır; çünkü diziler birbirine doğru yayılır.
Aynı sonucu reshape ile de elde edebilirsiniz, ama newaxis niyeti daha okunur gösterir. Çok eksenli dizilerde konumunu açıkça yazmak (örneğin [:, np.newaxis, :]) hangi eksenin eklendiğini netleştirir.
Bir uyarı: Dış işlemde sonuç boyutu girdi boyutlarının çarpımı kadar büyür. Her biri büyük diziler için sonuç belleği doldurabilir. Bellek riskine karşı şekilleri çalıştırmadan önce zihinsel olarak hesaplayın.
Döngüyü vektörel işleme çevirme kalıpları
Elinizde elemanları tek tek dolaşan bir for döngüsü varsa şu kalıplardan biri çoğu zaman yerine geçer:
- Aritmetik: Döngüdeki her elemana yapılan toplama, çarpma, kuvvet alma doğrudan a * b + c biçiminde yazılır. Karekök, üstel gibi matematik işlevleri için np.sqrt ve np.exp gibi evrensel işlevler (ufunc) dizinin tamamına uygulanır.
- Koşul: Döngüde if ile seçilen değerler np.where ile yazılır. Belgeye göre np.where(koşul, x, y) koşul doğruysa x, değilse y değerini seçer ve x ile y yayınlanabilir; skaler değer de verilebilir.
- Maskeleme: Bir koşulu sağlayan elemanları seçmek için boolean maske kullanılır: a[a > esik]. Eleman sayısı değiştiği için sonuç tek eksenlidir.
- Toplulaştırma: Döngüyle biriktirilen toplam, ortalama, en büyük değer sum, mean ve max işlevleriyle axis bağımsız değişkeni üzerinden alınır.
- Karşılaştırma: Dizilerin elemanlarını karşılaştıran döngü, a > b ifadesiyle boolean dizi üretir; ardından sum ile kaç eleman olduğu sayılır.
Örnek: Sütun standartlaştırma, yani her sütundan ortalamayı çıkarıp sapmaya bölme işlemi, döngüsüz şöyle yazılır:
z = (x - x.mean(axis=0)) / x.std(axis=0)
x.mean(axis=0) her sütun için bir değer verir; bu değerler satırlar boyunca yayılır. Aynı iş for ile sütun sütun dolaşmaya kıyasla hem daha kısa hem daha hızlıdır.
Pratik örnek: tüm noktalar arası mesafeyi döngüsüz hesaplamak
Bir müşteri konumu listesi için her müşteri çiftinin arasındaki uzaklığı bulmak, klasik bir iç içe döngü problemidir. Konumları (n, 2) şeklinde bir dizi olarak düşünün; n müşteri sayısı, her satır bir koordinat çiftidir.
fark = x[:, np.newaxis, :] - x[np.newaxis, :, :] mesafe = np.sqrt(np.square(fark).sum(axis=-1))
İlk satırda x birinci kullanımda (n, 1, 2), ikinci kullanımda (1, n, 2) şekline gelir; fark (n, n, 2) olur ve her çiftin koordinat farkını içerir. İkinci satır farkların karesini son eksen boyunca toplar (axis=-1) ve karekök alır; sonuç her çift için tek değer içeren (n, n) şekilli mesafe matrisidir.
Burada broadcasting'in gücü görünür: iç içe döngüler yerine birkaç satır. Maliyeti de görünür: Ara dizi (n, n, 2) şeklinde olduğu için müşteri sayısı arttıkça bellek ihtiyacı hızla büyür. Çok büyük n için parçalar halinde hesaplamak ya da bu iş için tasarlanmış kütüphane işlevlerini kullanmak gerekir.
Kendi problemlerinizde aynı yöntemi izleyin: Önce döngüyü mantıksal olarak tanımlayın (hangi eksenler üzerinde dönüyor?), sonra her eksen için bir boyut ayırın, gerekirse newaxis ekleyin ve son olarak indirgenecek ekseni sum ya da mean ile kapatın.
Sık hatalar ve ayıklama
Broadcasting sessiz hatalara yol açtığı için tehlikelidir. Şu durumlara dikkat edin:
- Beklenmeyen büyük sonuç. (n,) şekilli bir diziyle (n, 1) şekilli diziyi toplarsanız sonuç beklediğiniz vektör değil, (n, n) şekilli bir matris olur. Hata vermez; kodun sonraki adımında garip değerlerle ortaya çıkar. Kural: İşlemden önce shape yazdırın.
- Yanlış eksen. mean ya da sum için axis değerini tersine vermek aynı şekilli ama yanlış anlamlı sonuç üretir. Sonucun uzunluğunu beklediğiniz boyutla karşılaştırın.
- Görünmez bellek maliyeti. Yayılan dizi kopyalanmaz ama işlemin sonucu tam boyutta üretilir. Büyük ara diziler bellek hatasına yol açabilir.
- Yerinde işlem uyumsuzluğu. a += b biçimindeki yerinde işlemde b, a'nın şekline yayılabilmelidir; tersi mümkün değildir.
- Tür sorunu. Tam sayı dizisine ondalık sonuç yazılmaya çalışılırsa değer kırpılır ya da hata alırsınız.
- Her şeyi vektörelleştirme çabası. Okunabilirliği bozan, bellek tüketen dönüşümler değer katmaz. Gerçekten darboğaz olan döngüyü ölçüm yaparak (zaman ölçümü) bulun, yalnızca orayı dönüştürün.
Ayıklamak için basit bir yöntem: Karmaşık ifadeyi parçalara bölün ve her parçanın shape değerini yazdırın. Hata mesajındaki şekil çiftlerini sağdan sola okuyup hangi konumda uyuşmazlık olduğunu bulun.
Bu beceriyi Mindset programlarında nerede çalışırsınız?
Vektörel düşünme; sayısal analiz, risk ve finans modellemesi, görüntü ve sinyal işleme, makine öğrenmesi hazırlığı yapan analist ve yazılımcılar için pratik bir hız ve temizlik kazancı sağlar. Kodunuzu satır başına değil, dizi başına düşünmeye başladığınızda hem hata sayısı hem çalışma süresi azalır.
Python NumPy ile Sayısal Hesaplama programının modül başlıkları arasında indeksleme, dilimleme ve yayın (broadcasting), vektörel işlemler ve üniversal fonksiyonlar (ufunc) ile performans ve gerçek dünya uygulamaları bulunur. Büyük veri kümeleriyle çalışan ekipler için Pandas ve Polars ile Ölçeklenebilir Veri İşleme programı performans temellerini, bellek ve hız optimizasyonunu ele alan başlıklar içerir ve aynı vektörel düşünme alışkanlığının tablo düzeyindeki karşılığını sunar. Kurumsal veri ekibinde ortak kod incelemesi standardı olarak "gereksiz döngü" kontrolü bu programlardan çıkan pratik bir uygulamadır.
İlgili Mindset programı
Python NumPy ile Sayısal Hesaplama
Sık sorulan sorular
Broadcasting bellekte kopya oluşturur mu?
Yayılan küçük dizi için kopya oluşturulmaz; NumPy elemanları yeniden kullanarak işlemi yapar. Ancak işlemin sonucu tam boyutta yeni bir dizi olarak üretilir. Bu yüzden büyük dizileri dış işlemle birleştirdiğinizde sonuç belleği doldurabilir. Şekilleri önceden hesaplamak bu riski görmenin en kolay yoludur.
operands could not be broadcast together hatası ne demek?
NumPy dizilerin şeklini sondan başa doğru karşılaştırdı ve bir konumda boyutlar ne eşit ne de biri bir çıktı. Hata iletisi şekilleri gösterir. Çözüm, şekilleri yazdırıp hangi konumun uyuşmadığını bulmak, sonra reshape ya da newaxis ile boyut eklemek veya doğru ekseni seçmektir.
Vektörel işlem her zaman döngüden hızlı mıdır?
Büyük dizilerde ve temel aritmetikte genellikle evet, çünkü işlem derlenmiş kodda yürür. Çok küçük dizilerde, karmaşık koşul akışı olan işlemlerde ya da bellek açısından pahalı ara diziler yarattığında avantaj azalabilir. Ölçüm yapmadan varsayımla karar vermeyin; yavaş kısmı bulup yalnızca onu dönüştürün.
np.where ile boolean maske arasındaki fark nedir?
np.where(koşul, x, y) her konumda bir değer seçer ve sonuç koşulla aynı şekildedir. Boolean maske ise koşulu sağlayan elemanları ayıklar ve eleman sayısı azalır. Değerleri koşula göre değiştirmek istiyorsanız where, yalnızca belli elemanları almak istiyorsanız maske kullanın.
Broadcasting pandas'ta da çalışır mı?
Pandas, altta NumPy dizilerini kullandığı için benzer eleman bazlı işlem mantığı geçerlidir, ancak pandas etiketlere göre hizalama yapar. Serileri topladığınızda eşleşen indeksler toplanır, eşleşmeyenler eksik değer olur. Bu yüzden NumPy'deki konum tabanlı yayın ile pandas'taki etiket tabanlı hizalamayı birbirine karıştırmayın.
İlgili rehberler
İlgili eğitimler
Kategori: Veri Analitiği ve İş Zekası, Yazılım Geliştirme