Home Arrow Icon Knowledge base Arrow Icon Global Arrow Icon Push vs Concat'ı büyük dizilerde kullanmanın performans sonuçları nelerdir?


Push vs Concat'ı büyük dizilerde kullanmanın performans sonuçları nelerdir?


Push ve Concat'a büyük dizilerde kullanmanın performans sonuçları, öncelikle bu yöntemlerin dizi birleştirme veya element eklemenin yanı sıra altta yatan bellek yönetimi ve hesaplamalı ek yüklerinin yanı sıra farklı yollardan kaynaklanmaktadır.

Array.push kullanılırken, bir diziden öğeler doğrudan mevcut diziye eklenir. Birleştirme dizileri için, bu genellikle uygulamayı kullanmak gibi bir desen veya bir kerede birden fazla öğeyi bastırmak için yayılma operatörünü içerir, örneğin Array.prototype.push.Apply (ARR1, ARR2). Bu yaklaşım orijinal diziyi yerinde değiştirir ve genellikle doğrusal zaman, O (n) 'de gerçekleştirilir, burada n itilen öğelerin sayısıdır. Bunun nedeni, push'un yeni bir dizi oluşturmadan veya tüm içeriği tekrar tekrar kopyalamadan öğeleri mevcut dizinin sonuna eklemesidir. Bu yerinde mutasyon nedeniyle, bellek ek yükü en aza indirilir ve yöntem genellikle optimize edilmiş bitişik bellek bloklarını ve önbellek yeri kullanır ve bellek erişim maliyetini azaltır.

Buna karşılık, Array.concat orijinal dizileri değiştirmez. Bunun yerine, birlikte birleştirilen orijinal dizilerin öğelerini içeren yeni bir dizi oluşturur. Bu yeni dizinin oluşturulması, dizilerin birleşik boyutu için bellek tahsis edilmesini ve her iki kaynak dizideki öğeleri kopyalamayı bu yeni tahsis edilen alana içerir. Bu kopyalama, genellikle her iki dizinin boyutu ile orantılı bir yük getirir, bu da işlemin zaman karmaşıklığını O (M + N) haline getirir, burada m ve n, birleştirilen dizilerin boyutlarıdır. Yeni bir dizinin oluşturulması ve veri kopyalaması, artan bellek kullanımı ve özellikle çok büyük dizilerle fark edilebilir, çöp toplama tetikleme olasılığı daha yüksektir.

Benchmark testleri, itme işleminin, çok sayıda eleman birleştirme veya eklemeyi içeren operasyonlar için önemli ölçüde daha hızlı olabileceğini göstermektedir. Örneğin, bir kıyaslama, dizileri birleştirmenin binlerce elemanla tekrar tekrar birleştirilmesi için itme, Chrome'daki Concat'tan yaklaşık 945 kat daha hızlı ve Firefox'ta daha hızlı olduğunu gösterdi. Bu büyük fark, Concat'ın yeni bir dizi oluşturma ve veri kopyalama davranışından kaynaklanırken, Push mevcut diziyi daha kademeli ve yerinde büyütür ve tekrarlanan bellek reaksiyonlarından kaçınır.

Ancak, bu performans özellikleri kullanım senaryolarına bağlı olarak değişebilir. Amaç, önceden tahsis edilmiş iki çok büyük dizinin tek bir birleşmesiyse, Concat bir kez tahsis ettiği ve kopyayı bir kez yaptığı için nispeten iyi performans gösterebilir. Bu gibi durumlarda, Push'un tek tek veya toplu ekleme yaklaşımı, teorik avantajını azaltabilecek çoklu yeniden tahsislere veya dahili olarak kopyalamaya neden olabilir. Bununla birlikte, birçok dizide tekrarlanan birleştirme veya birçok öğe eklemek için, push ek olarak o (1) amortismana eğilimindedir, çünkü diziler genellikle bellek geometrik olarak (aşıldığında ikiye katlama kapasitesi) tahsis ederek genel olarak yüksek verimli hale getirir.

Bellek perspektifinden bakıldığında, Push'un yerinde mutasyonu, daha az sık tahsis ve bellek alt sisteminde potansiyel olarak daha az zorlama anlamına gelir. Yeni tahsisler gerektiren Concat yöntemi ve verileri yeniden bir araya getirir, özellikle büyük diziler için belleği vurgular ve daha fazla önbellektir. Bu durum, CPU önbellek limitlerini aşarak, daha yüksek gecikmeli önbelleklerden veya ana bellekten gelen verilerin getirilmesi nedeniyle daha yavaş bellek erişim sürelerine yol açan konsantrasyon işlemlerinin muhtemelen daha yavaş bellek erişim sürelerine yol açar. İtme, dizideki zaten verilere yeniden bakıldığından kaçınarak önbellek yerini daha iyi kullanabilir.

Push'un orijinal diziyi değiştirdiğine dikkat edilmelidir, Concat yeni bir dizi döndürerek değişmezliği korur. Bu fark uygulama tasarımında önemlidir, ancak performansı da etkiler. Konsat ile değişmez birleştirme, yan etkiyi garanti etmez, ancak ekstra bellek ve kopyalama fiyatını öderken, Push kaynak dizisini doğrudan değiştirerek hız için değişmezlikten kaçınır.

Bazı nüanslar, JavaScript motorlarının bu işlemleri bağlam ve karmaşıklığa göre farklı şekilde optimize edebileceğini içerir. Örneğin, motorlar sabit tipleri veya küçük dizileri daha agresif bir şekilde optimize eder. Ayrıca, Concat'ın yöntem imzası, aynı anda birden fazla dizi ve değeri eklemeyi destekler (Â aşırı yüklenmiş imzalar ”), havai ekleyen dahili düzleştirme ve kopyalama adımları gerektirirken, itme bu tür düzleştirilmeden doğrudan öğeler ekler.

Çöp toplama ile ilgili olarak, Concat'ta yer alan sık tahsisler çöp toplama iş yükünü artırabilir, çünkü eski diziler kopyaladıktan sonra atılır. Bu, yüksek tahsis senaryolarında duraklamalara veya performans düşüşlerine yol açabilir. Mevcut bir dizi büyüyen Push, tahsislerin frekansını ve dolayısıyla çöp toplama yükünü azaltır.

Genel olarak, push ve concat arasında seçim, hız (itme) ile değişmezlik/kolaylık (concat) arasında bir dengeyi içerir. Bir öncelik olarak performansa sahip büyük dizilerdeki işlemler için, itme genellikle daha verimli bellek kullanımı ve daha düşük ek yükü nedeniyle tercih edilen yöntemdir. Concat'ın dizi oluşturma ve kopyalama yükü, dizi boyutları arttıkça çok maliyetli hale gelir. Değişmezliğin kritik olduğu senaryolarda, performans cezasına rağmen Concat kullanılır.

Özetle, Push, yerinde modifikasyon, amortismanlı sabit zaman ekleri ve azaltılmış kopyalama nedeniyle büyük diziler bağlamında konsantreye kıyasla tipik olarak daha iyi performans ve daha düşük bellek ek yükü sergiler. Concat, ek bellek tahsisleri ve kopyalama maliyetlerinden muzdariptir, çünkü her çağrıldığında yeni bir dizi oluşturur, bu da alınan zamanı hem de bellek kullanımını, özellikle çok büyük dizilerle etkiler. Bu farklılıklar, birçok diziyi birleştirirken veya büyük veri setleriyle uğraşırken büyütülür, burada itme ölçütlerine göre Concat'tan yüzlerce ila binlerce kat daha hızlı olabilir. Bununla birlikte, kullanım bağlamına ve motor optimizasyonlarına bağlı olarak, bu genel kalıplar istisnalara sahip olabilir ve kod değişmezliği ve sürdürülebilirlik ihtiyacının yanı sıra dikkate alınmalıdır.