Was ist die optimale Puffergröße für einen Stream von HttpWebResponse.GetResponseStream ()?
Online-Beispiele variieren von 256b bis zu 5Kb. Was gibt? Ich nehme an, Puffergrößen können situationsbedingt sein. Wenn ja, in welchen Situationen soll welche Art von Puffergröße verwendet werden?
Danke.
Wirklich ist es nicht sehr wichtig.
Sicher, wenn Sie wirklich kleine Puffer verwenden, müssen Sie möglicherweise ein paar zusätzliche Aufrufe über die Schichten durchführen, um die Bytes zu erhalten (obwohl der Strom wahrscheinlich zumindest eine Pufferung macht - ich weiß nicht, was es Standard ist) sind). Und sicher, wenn Sie wirklich große Puffer verwenden, verschwenden Sie etwas Speicher und bringen eine gewisse Fragmentierung mit sich. Da Sie offensichtlich IO hier tun, wird jedes Mal, wenn Sie durch das Optimieren der Puffer gewinnen, von der IO-Zeit dominiert werden.
Als allgemeine Regel gehe ich mit einer Zweierpotenz zwischen 2048 (2k) und 8192 (8k). Stellen Sie nur sicher, dass Sie wissen, was Sie tun, wenn Sie mit einem Puffer gleich oder größer als 85.000 Bytes gehen (es ist dann ein " großes Objekt "und unterliegt verschiedenen GC-Regeln ).
In der Tat ist es wichtiger als die Puffergröße, wie lange Sie sie halten. Für Objekte außerhalb des großen Objektspeichers ist der GC sehr gut im Umgang mit sehr kurzlebigen Objekten (Gen 0-Sammlungen sind schnell) oder sehr langlebigen Objekten (Gen 2). Objekte, die lange genug leben, um zu Gen 1 oder 2 zu gelangen, bevor sie befreit werden, sind vergleichsweise kostspieliger und normalerweise lohnt es sich viel mehr, sich Gedanken darüber zu machen, wie groß der Puffer ist.
Eine letzte Anmerkung: Wenn Sie aufgrund der Größe der Puffer, die Sie verwenden, ein Leistungsproblem haben, testen . Es ist unwahrscheinlich, aber wer weiß, vielleicht haben Sie ein seltsames Zusammentreffen von Betriebssystemversion, Netzwerkhardware und Treiberversion, die ein gewisses Problem mit bestimmten Puffern hat.
Meine anekdotenhafte Erfahrung war, dass es wirklich davon abhängt, was Sie tun, aber normalerweise würde irgendetwas im Bereich von 1024-4096 Bytes (1-4KB aka Power von zwei) mir eine vergleichbare Leistung geben (wobei 4KB die " beste "Nummer, die ich gesehen habe).
Grundsätzlich möchten Sie einen Puffer groß genug, damit Sie nicht unnötig Daten aus dem Stream lesen, aber nicht so groß, verringern Sie die Renditen. Wenn Ihr Puffer zu groß ist (~ MBs), erhöhen Sie die Anzahl der Speicher-Cache-Fehler, wodurch Ihre Leistung möglicherweise beeinträchtigt wird. Natürlich variiert dies stark aufgrund der tatsächlichen H / W (Busgeschwindigkeit, Cache-Größe usw.), aber ich habe Fälle, in denen ein 4MB Puffer langsamer war als der 4KB Puffer (beide hatten eine lange Lebensdauer, GC nicht) ein Problem).
Wie Jonathan bemerkt, testen Sie Ihre aktuelle Implementierung, bevor Sie vorzeitige Optimierungen versuchen.
Eigentlich habe ich Probleme, wenn die Puffergröße zu klein ist. Ich habe es getestet und verifiziert, dass die Puffergröße nicht auf einen kleinen Wert eingestellt werden sollte. In meinem Beispiel habe ich es auf 2048 gesetzt und der Download wird SEHR LANGSAM im Vergleich zu Firefox (Firefox ist auch ohne Download-Segmentierung, genau wie meines).
Und nachdem ich es auf eine große Größe 409600 eingestellt habe, ist der Download viel schneller, ich denke, dass ein zusätzlicher Anruf Overhead kostet oder so, dass der Download langsam wird. Vielleicht überschreitet der Puffer in der Netzwerkebene Ihre Puffergröße, so dass der TCP erneut das Paket erneut senden muss? (Nur eine Vermutung, da ich nicht weiß, wie TCP funktioniert), aber kleine Puffergröße verlangsamt definitiv meinen Download. Ich habe es getestet, indem ich mit Firefox Standard-Download (ohne Add-On und Segmenetation) ausgeführt und meine Klasse verwendet, beide sind viel zu unterschiedlich.
Jetzt ist es viel schneller, jedes Mal, wenn es eine Schleife macht, wird es ungefähr 200000 Bytes (200Kb) lesen, da die Verbindung hier ruhig schnell ist, aber nachdem ich zwei Threads laufen lasse, wird es viel langsamer, wahrscheinlich muss es mit einem anderen teilen thread.
Tags und Links .net buffer httpwebresponse