Sadece "evet ya da hayır demiştim ya da hayır demiştim" deyince, UDP ile yüzleşmek zorunda kalmayacağınız bir sürü sorunla mücadele etmek için kendinizi açıyor olabilirsiniz.
Buradaki diğer cevapların hiçbiri, bunu kanıtlamanın açık yolunu belirtmiyor.
Bazı basit gerçekleri al
- Bir IP başlığı, hangi protokolü kullanırsanız kullanın, 20 bayttır.
- UDP başlıkları 4 bayttır
- TCP başlıkları 20 bayttır
Dolayısıyla, her satır için 1 baytlık bir mesaj gönderdiğinizde, bir IP başlığının da gerekli olduğunu varsayan protokole bağlı olarak aslında 25 veya 41 bayt gönderdiniz.
kaynaklar:
Benim tavsiyem
Durumunuzu istemci-sunucu etkileşimine ihtiyacınız olan yerde alın, müşteri sayısını tahmin edin, sonra ikisi arasında gönderdiğiniz verilere göre hesaplamayı yapın.
Bir örnek
Oyunumda güncelleme başına her biri 1 bayt olan 10 mesaj gönderdiğimi ve yaklaşık 60 fps güncellediğimi varsayalım, böylece gerçek mesaj verisinin saniyesinde 60 * 10 = 600 bayt + ilgili başlıkları göndermem gerekiyor.
Şimdi oyuna bağlı olarak, hepsini tek bir mesaj olarak gönderebildiğim için TCP katmanından ek yüküm sadece 40 bayttır (etkin saniyede 20 bayt UDP maliyeti), bu ek yüke sahip olmamak, potansiyel olarak 600 bayt maliyettir ( çünkü tüm ileti akışını tekrar göndermem gerekebilir).
Bununla birlikte, her mesajın gönderilmeye hazır olduğu anda kendi başına gönderilmesi hayati önem taşıyorsa, 600 mesajım var (ayrıca 600 bayt) + 40 * 600 = 24k değerinde TCP ek yükü veya saniyede ~ 14k UDP ek yükü + 600 bayt mesaj verisi.
Yine, şu soruları soruyoruz, bu mesajların ne kadar hayati olduğu, ne sıklıkta oldukları ve genel giderlerin azaltılması için bir şekilde bir araya getirilebilirler mi?
Bu sadece bir sürü bayt mesajına dayanıyor, tipik olarak çok farklı bir şeyler yaparsınız, ancak ham verinin TCP'nin UDP'den daha iyi bir durumda olup olmadığını ispatlamak zor olduğunu bilmeden.
Yani işe yarayacak mı?
Tipik bir fps'niz varsa ve konum önemliyse (aldatma veya yanlış kararları önlemek için), ağ akışınızın uyumlu olduğunu bilmeniz gerekir, ancak her biri 24k + iletinin akıp gittiği 32 oynatıcı (yani 768KB / s + mesajlar) ... bu, her bir istemciden bir sunucu aracılığıyla diğer tüm istemcilere her kare için en az 1 mesaj göndermeye dayanan ayrı başlıklar için bir 10mb / s genişbant hattı ile ilgilidir.
Açıkçası sunucunuzu ve istemcinizi bu şekilde çalışacak şekilde kodlamayacaksınız ve mesaj boyutlarının çoğu durumda daha büyük ve muhtemelen kare başına 1 bayttan biraz daha az olması muhtemeldir, bu nedenle gerçek bir dünya görmeden söylemek zor "bu, göndermem gereken veriler" örneği.
Benim olayım
Durumumu makul bir yükü olarak yaptım, ancak bu, mesaj akışlarımı nasıl oluşturduğuma dayanıyor, bu yüzden bazı tasarımlara kıyasla çok fazla genel masrafa sahip değilim.
TCP iyi çalışıyor ve ölçeklenebilir bir MMO sunucusu ve istemci çerçevem var, ancak çağrılarımı toplayabildiğim için çok fazla veriyi çerçeve veya çok sayıda küçük paket akışına göndermem gerekmiyor.
diğerleri için: TCP sadece yapmayacak ve sadece UDP'yi kullanabilirler ancak ne aldıklarına dair kendilerine güvence vermeyeceklerini kabul etmek zorundadırlar (sipariş / varış garantisi).
Diğer hususlar
Birçok kötü kodlanmış oyun motoru, işlemci üzerindeki ana iş parçacığındaki her şeyi kullanır, böylece CPU'ya genellikle ağ kodunu işlemek için çok az zaman verilir, hem hizmet hem de müşterinin düzgün bir şekilde uygulanması tamamen asenkron ve muhtemelen zorlanır ve mesajları gruplar halinde çekin.
Dışarıda bazı iyi ağ kütüphaneleri var ama burada görüldüğü gibi, birçoğunun UDP'nin "sadece daha iyi" olduğu, ilk önce kendi ihtiyaçlarınızda iyi bir faktör olduğu ve durum böyle olmadığı ve olmayan bir kütüphane bulduğu görüşünde olduğu görülüyor. Yaptığınız şeydeki faktör, aynı lib'deki UDP varyantına kıyasla kötü kodlanmış bir TCP kurulumuna neden olabilir (sadece bunu gördüm ve yükleme testleri bunu kanıtladı).
Öncelikle göndermek istediğiniz verinin teknik temelini oluşturun ve test edin, sonra ölçeklendirmek için matematik yapın, en kötü durum yükü bir buluta dağıtarak test edin ve 50 bilgisayarın test edip edemeyeceğini görmek için bir test istemcisi çalıştırmasını sağlayın Oyun başına 32 oyuncu limitiniz (veya sahip olabileceğiniz herhangi bir limit).