Aşağıda, yüksek performanslı bir soket bileşeni uygulamadaki sorunların özeti verilmiştir; eğer sadece binlerce eşzamanlı uygulamayla uğraşmanız gerekiyorsa, kod yazımına dikkat edebilirsiniz, ancak on binlerce veya on binlerce eşzamanlı uygulamayla karşılaşmanız gerekir. Aşağıdaki soruların özetinin bu başvurunun yazımında büyük katkı sağladığına inanılır.
SocketAsyncEventArgs
Bu nesne, .NET 2.0 sp1'den sonra sağlanır ve esas olarak yüksek performanslı soket veri gönderme ve alma işlemini uygulamak için kullanılır (daha ayrıntılı bir giriş için MSDN'ye gidebilirsiniz). Bu nesne, ilgili göndermeleri göndermek ve almak için tamponları ayarlamak için üç yol sunar: SetBuffer(Int32, Int32), SetBuffer(Byte(), Int32, Int32, BufferList; ilk ikisi ikincisiyle birlikte var olamaz ( MSDN nedenini açıklıyor). Bir Buffer ayarladığınızda, ister SetBuffer(Byte(), Int32, Int32) ister BufferList olsun, program ömrü boyunca SocketAsyncEventArgs örneği başına sadece bir kez ayarlamayı deneyin, çünkü bu ayar çok kaynak gerektirebilir. SocketAsyncEventArgs inşası sırasında veri tamponunun SetBuffer(Byte(), Int32, Int32) üzerinden ayarlanması ve ardından SetBuffer(Int32, Int32) kullanılarak işlenilmesi önerilir. BufferList kurmak istediğinizde, <byte>IList tarafından referans verilen bayt[] kaynağını değiştirmemek en <ArraySegment>iyisidir. Değiştirilirse, SocketAsyncEventArgs tamponu yeniden bağlayacak ve verimliliği etkiler.
SocketAsyncEventArgs pool
Yukarıda belirtildiği gibi, bu hedefe ulaşmak için SocketAsyncEventArgs tarafından referans verilen tamponu mümkün olduğunca değiştirmemeye çalışın. Bu nedenle, bir SocketAsyncEventArgs uygulama havuzu oluşturmak ve programın başında SocketAsyncEventArgs nesnesini mümkün olduğunca başlatmak gereklidir. SocketAsyncEventArgs oluşturulmasını azaltmanın yanı sıra, havuzlar oluşturmak da büyük ölçüde bellek tasarrufu sağlayabilir. Temel sebep, her mesajın ne kadar büyük olduğunu bilememeniz; tabii ki, tasarımdan önce mesaja maksimum bir sınır koyup ardından SocketAsyncEventArgs'a karşılık gelen tamponu ayarlayabilirsiniz. Ancak bu büyük bir hafıza israfıdır, çünkü tüm mesajların maksimum uzunluğu yoktur. SocketAsyncEventArgs'a uygun miktarda tampon boyutu tahsis edin, havuzlar üzerinden çağrılar sağlayın ve bir veya daha fazla SocketAsyncEventArgs'a esnek bir mesaj yazabilir veya işlem için birden fazla mesajı bir SocketAsyncEventArgs'a depolayın.
kuyruk
Birçok uygulamanın iş parçacıklarını doğrudan açmak veya veri aldıktan sonra iş parçacığı havuzuna atmak olduğunu görüyorum, ki bu çok kötü çünkü iş parçacıklarının işini daha iyi kontrol etmiyor, hatta iş parçacıklarının bekletilmesini de dahil. Özel iş parçacıkları + kuyruklar ile, kaç iş parçacığının hangi işten sorumlu olduğunu kontrol edebilirsiniz ve sıraya alınan iş sadece kuyruğun içinde olur; Çok sayıda iş parçacığı veya çok sayıda hat beklemeyecek, bu da iş parçacığı planlaması nedeniyle işletim sisteminin kaynak kaybına yol açacaktır.
Gecikmiş veri birleştirilmesi
Gecikmeli birleştirme veri iletimi, birçok senaryoda kullanılmayan ancak oyun sunucularında yaygın, aşırı ağ IO işlemleri sorununu çözmenin bir yoludur. Daha önce biri bana bir soru sordu, sahnede 400 kullanıcı varsa, her kullanıcının ortam değişikliği diğer kullanıcılara bunu bildirecek. Birleşik veri kullanılmazsa, IO işlem numarası sisteminin taşıması zor olan çok korkutucu bir ağ IO operasyonu oluşturur. Bu nedenle, mevcut uygulama için uygun bir gecikme aralığında veri birleştirip göndermek gereklidir. |