Gibt es eine optimale Größe in byte für das senden von Daten über ein Netzwerk?
Ich nehme 100 bytes ist zu klein und kann verlangsamen größere Datei überträgt-mit all den schreibt, aber so etwas wie 1MB scheint, wie es kann zu viel sein. Hat jemand irgendwelche Vorschläge für eine optimale chunk bytes pro schreiben für das senden von Daten über ein Netzwerk?
Zu erarbeiten, ein bisschen mehr, ich bin Implementierung von etwas, das sendet Daten über eine Netzwerkverbindung und zeigt den Fortschritt an, dass Daten gesendet werden. Ich habe gemerkt, wenn ich das senden von großen Dateien über 100 bytes zu schreiben, ist es extrem langsam, aber die Fortschritt-bar arbeitet heraus, sehr schön. Allerdings, wenn ich bei sagen wir 1M pro schreiben, es ist viel schneller, aber die progress bar funktioniert nicht so gut wegen der größeren Brocken gesendet wird.
- wäre es nicht angewiesen auf die senden-Protokoll?
- Ein byte-Größe von 0 optimieren Sie Ihre pro-Paket-speed, aber wäre suboptimal für die gesamte Zeit übertragen.
- Ich Stimme mit Mitch Weizen - wenn Sie mit TCP, dann, sofern du Sie aktiviert hast NODELAY oder flush, werden die Pakete gesendet werden, indem die Stapel entsprechen nicht auf Ihre Anrufe zu senden, sowieso. Überprüfen Sie für ioctls in Bezug auf die Ausgabe-Puffer - vielleicht sind Sie in der Lage zu verbessern, den Fortschritt-bar, oder schreiben in den buffer-Größe Brocken.
Du musst angemeldet sein, um einen Kommentar abzugeben.
Wenn du kannst, lass mal den IP-stack umgehen, die meisten Betriebssysteme haben eine Menge Optimierung bereits integriert. Vista, zum Beispiel, wird dynamisch verändern verschiedener Parameter, um den Durchsatz zu maximieren; zweitens-raten der Algorithmus ist unwahrscheinlich, nützlich sein.
Dies ist vor allem in höheren Sprachen, die weit von der eigentlichen Draht, wie C#; gibt es genügend Schichten zwischen Ihnen und der TCP/IP-Pakete, die ich erwarten würde, den code haben relativ wenig Einfluss auf den Durchsatz.
Im schlimmsten Fall, testen Sie verschiedene message-Größen, in verschiedenen Situationen für sich selbst; einige Lösungen sind one-size-fits-all.
Nein, es gibt keine universal optimale byte-Größe.
TCP-Pakete sind abhängig von der Fragmentierung, und zwar wäre es schön, davon ausgehen, dass alles von hier aus zu Ihrem Ziel wahre ethernet mit großen Paketgrößen, die Realität ist, auch wenn Sie können, Holen Sie sich die Paket-Größen aller einzelnen Netzwerke eines deiner Pakete nimmt, jedes Paket, das Sie senden kann einen anderen Weg durch das internet.
Es ist nicht ein problem, können Sie "lösen" und es gibt keine Universelle Größe ideal.
Feed die Daten an das Betriebssystem und die TCP/IP-stack so schnell wie Sie können, und es werden dynamisch die Anpassung der Paketgröße an die Netzwerk-Anschlüsse (Sie sollten sehen, den code, die Sie verwenden für diese Optimierung - es ist wirklich, wirklich interessant. Zumindest auf die besser stapeln.)
Wenn Sie Steuern alle Netze und Stapel verwendet wird, und zwischen Ihren clients/Servern, wenn, dann Sie tun können, etwas hand-tuning. Aber in der Regel selbst dann hätten Sie ein wirklich gutes Verständnis des Netzwerkes und die Daten zu senden, bevor ich schlage vor, dass Sie sich ihm nähern.
-Adam
Wenn Sie mit TCP/IP über Ethernet, die maximale Paket-Größe von 1500 Byte. Wenn Sie versuchen, zu senden mehr als, dass auf einmal, werden die Daten aufgeteilt in mehrere Pakete, bevor Sie verschickt wird auf den Draht. Wenn die Daten in Ihrer Anwendung ist bereits paketiert, dann möchten Sie vielleicht wählen Sie eine Paketgröße von knapp 1500, so dass, wenn Sie senden Sie ein vollständiges Paket, das zugrunde liegende Stapel nicht zu brechen it up. Zum Beispiel, wenn alle senden, die Sie tun, ist 1600 bytes, die den TCP-stack gesendet werden müssen, zwei Pakete für jeden senden, mit der zweiten Pakets, das meistens leer. Das ist ziemlich ineffizient.
Having said, die, ich weiß nicht viel von einem sichtbaren Auswirkungen auf die Leistung haben wird.
Ich glaube, dein problem ist, dass Sie blockierende sockets und nicht nicht-blockierende lieben.
Wenn Sie blockierende sockets und senden Sie 1M Daten der Netzwerk-stack warten kann, bis alle Daten in einen Puffer, wenn die Puffer voll sind, werden Sie blockiert werden, und Ihre Fortschritte bar wartet für die ganze 1M akzeptiert zu werden, in den Puffer, das kann eine Weile dauern, und dein Fortschrittsbalken wird nervös.
Wenn Sie jedoch die Verwendung von nicht-blockierende sockets, was Puffergröße Sie verwenden, wird nicht blockiert, und Sie müssen zu tun, die darauf warten, dich mit select/poll/epoll/was auch immer-arbeiten-auf-Ihre-Plattform (wählen Sie die meisten tragbaren aber). Auf diese Weise werden Ihre Fortschritte bar wird schnell aktualisiert und spiegeln die genauesten Informationen.
Tun, beachten Sie, dass beim sender der Fortschrittsbalken ist teilweise gebrochen irgendeiner Weise seit der kernel-buffer einige Daten und Sie werden 100% erreichen, bevor die andere Seite wirklich die Daten erhalten. Die einzige Weise um dieses ist, wenn das Protokoll enthält eine Antwort auf die Menge der empfangenen Daten durch den Empfänger.
Wie andere gesagt haben, die zweiten raten, das OS und das Netzwerk ist meistens zwecklos, wenn Sie zu halten mit blocking sockets wählen Sie eine Größe, die groß genug ist, um mehr Daten umfassen, als ein einziges Paket, so dass Sie nicht senden, zu wenig Daten in ein Paket, wie dies reduzieren Sie Ihren Durchsatz unnötig. Ich würde mich mit so etwas wie 4K, darunter mindestens zwei Pakete auf einmal.
Die eine Sache, die ich hinzufügen wird, ist, dass für eine bestimmte ethernet-Verbindung, dauert es etwa so lange zu senden ein kleines Paket als einen großen. Andere haben gesagt: wenn Sie nur das senden einen Strom von Daten, lassen Sie das system umgehen. Aber wenn Sie sich sorgen um einzelne kurze Nachrichten hin und her, ein typische ethernet-Paketgröße von rund 1500 Byte - wie lange halten Sie es unter, dass Sie sollte gut sein.
Würden Sie verwenden müssen Pfad-MTU-Erkennung, oder verwenden Sie eine gute default-Wert (also weniger als 1500 bytes).
Machen Sie eine Funktion mit dem Namen CalcChunkSize
Fügen Sie einige private Variablen der Klasse:
Vor jedem download ein Stück prüfen, ob seine Zeit, um neu berechnen chunksize mit der ChunkSizeSampleInterval
numIterations auf 0 gesetzt ist außerhalb der download-Schleife und nach jedem heruntergeladen chunk zu numIterations += 1
Haben die CalcChunkSize, dies zu tun:
Dann verwenden Sie einfach die ChunkSize bei der Beantragung nächsten chunk.
Fand ich diese in das "Senden von Dateien in chunks mit MTOM-web-services und .Net 2.0" von Tim_mackey und fand es sehr hilfreich mich selbst zu dynamisch berechnen effektivste chunksize.
Den Quellcode im ganzen sind hier: http://www.codeproject.com/KB/XML/MTOMWebServices.aspx
Und Autor hier: http://www.codeproject.com/script/Membership/Profiles.aspx?mid=321767
Einen empirischen test, den Sie tun können, wenn Sie nicht bereits haben, ist natürlich die Verwendung eines sniffers (tcpdump, Wireshark, etc.) und schauen, was Paketgrößen werden erzielt, wenn unter Verwendung anderer software für up - /Download. Das könnte einen Hinweis darauf geben.
Hier ist die Formel, die Sie brauchen:
Verwendung dieser, ist jeder chunk, den Sie senden, erhöhen Sie den Fortschrittsbalken um 1 pixel. Ein kleiner chunk-Größe ist sinnlos, in Bezug auf Benutzer-feedback.