65 Stimmen

.NET MemoryStream zurücksetzen oder löschen

Der .NET MemoryStream scheint keine .Reset- oder .Clear-Methode zu haben.

Ich dachte daran, den folgenden Code zu verwenden, um dies zu erreichen:

ms.Seek(0, IO.SeekOrigin.Begin)
ms.SetLength(0)

Wie kann ich einen vorhandenen .NET MemoryStream löschen oder zurücksetzen?

107voto

Andrew Bezzub Punkte 15286

Warum müssen Sie den Speicherstrom zurücksetzen? Sie können jederzeit eine neue Datei erstellen. Oder Sie können verwenden:

memoryStream.SetLength(0);

34voto

Rana Ian Punkte 684

Da ein MemoryStream im Wesentlichen ein Byte-Array mit einem Index (und einigen anderen unterstützenden Elementen) ist, kann das Löschen des Byte-Arrays und das Zurücksetzen des Index als Zurücksetzen und Löschen des MemoryStreams betrachtet werden. Wenn der Ausgangszustand eines MemoryStream ein Array mit der Position Null ist, könnte ein Beispiel für einen MemoryStream-Reset sein:

public static void Clear(this MemoryStream source)
{
  byte[] buffer = source.GetBuffer();
  Array.Clear(buffer, 0, buffer.Length);
  source.Position = 0;
  source.SetLength(0);
}

Es ist nicht korrekt zu sagen, dass MemoryStream.SetLength allein den MemoryStream zurücksetzt oder löscht, da SetLength das interne Puffer-Array nur dann löscht, wenn die Länge die aktuelle Pufferlänge überschreitet.

Die Neuinitialisierung eines MemoryStreams ist ein guter Ansatz, aber weniger effizient. Ein Vorteil der Neuinitialisierung des MemoryStream wäre die Garantie, dass der Stream nie geschlossen wurde. Sobald der MemoryStream geschlossen ist, kann er nicht mehr geändert werden. Wenn Sie sicherstellen können, dass die MemoryStream-Instanz nicht geschlossen wird, kann das Löschen des Puffers der richtige Weg sein.

1voto

bunjeeb Punkte 1045

Ich habe DotMemory zum Profil @Rana_Ian Lösung, und ich rief GC, um die vollständige Sammlung zu erzwingen. Ich fand, dass große Ströme wird eingeklebt LOH ! Und nach Hinzufügen einer zusätzlichen Zeile

public static void Clear(MemoryStream ms)
{
    var buffer = ms.GetBuffer();
    Array.Clear(buffer, 0, buffer.Length);
    ms.Position = 0;
    ms.SetLength(0);
    ms.Capacity = 0; // <<< this one ******
}

Ich klickte auf F12 zu sehen Capacity Implementierung, Und ich habe das gefunden (ich habe den generierten Code ein wenig vereinfacht - ich verwende Resharper):

public virtual int Capacity
{
  get
  { .... // some code }
  set
  {
    if ((long) value < this.Length) { // throw some ex }
    if (!this._isOpen) { // some another code }
    if (!this._expandable && value != this.Capacity) { //MemoryStreamNotExpandable }
    if (!this._expandable || value == this._capacity) return;
    if (value > 0)
    {
      byte[] numArray = new byte[value];
      if (this._length > 0)
        Buffer.InternalBlockCopy((Array) this._buffer, 0, (Array) numArray, 0, this._length);
      this._buffer = numArray;
    }
    else
      this._buffer = (byte[]) null; /// <<<< that's it! I need this one
    this._capacity = value;
  }
}

Es löscht also den Puffer, ich bin mir nicht sicher, ob das richtig ist oder nicht!

-5voto

omglolbah Punkte 297

Der memorystream verfügt nicht über eine Reset/Clear-Methode, da dies redundant wäre. Durch Setzen der Länge auf Null wird er gelöscht.

Das kann man natürlich immer machen:

memoryStream = new MemoryStream(memoryStream.Capacity());

Dies würde einen Memorystream der gleichen Größe ergeben, der initialisiert wird.

Wenn Sie den Stream wirklich manuell löschen wollen, müssten Sie vermutlich eine Schleife durch die Elemente ziehen.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X