Domanda

Come discusso prima , quando un BinaryReader o BinaryWriter viene chiuso, anche il suo Stream sottostante viene chiuso (aargh). Considera questa situazione: a un R di routine viene passato un MemoryStream, ad esempio M ; Vorrei scrivere alcune cose su M e poi passarle a un'altra routine per ulteriori elaborazioni (non necessariamente scrivendo). Per comodità, vorrei avvolgere M in un BinaryWriter per scrivere. Dopo aver scritto, ho finito con BinaryWriter ma non con M .

void R(MemoryStream M)
{
    using (B = new BinaryWriter(M))
    {
        // write some stuff using B
    }

    S(M);  // now pass M to another routine for further processing
}

Ma non riesco a smaltire BinaryStream senza chiudere M .

D: Esiste un modo per eseguire una delle seguenti operazioni?

  • estrae il byte sottostante [] da un MemoryStream,
  • clonare uno Stream
  • riapri uno Stream dopo che è stato chiuso
È stato utile?

Soluzione 4

Grazie a diversi che hanno suggerito ToArray, sono stato portato alla risposta giusta, che è "M.GetBuffer". ToArray non è poi così male, ma

  • crea una copia
  • ottiene solo una parte del buffer

GetBuffer prende semplicemente un riferimento al byte sottostante [], che è quello che sto cercando.

Altri suggerimenti

Dovresti ottenere meglio il buffer byte [] sottostante usando

byte[] buffer = ms.GetBuffer();

E quindi copiare i dati byte usando il metodo Array.Copy (). Sei libero di creare un nuovo stream con esso.

Puoi usare cose come MiscUtil.IO.NonClosingStreamWrapper in MiscUtil , che racchiude un Stream e ignora semplicemente le richieste Close / Dispose . Proprio per questo scopo.

void R(MemoryStream M)
{
    using (B = new BinaryWriter(new NonClosingStreamWrapper(M)))
    {
        // write some stuff using B
    }

    S(M);  // now pass M to another routine for further processing
}    

Puoi:

  • Chiama M.ToArray () per ottenere lo stream come una matrice di byte.
  • Sottoclasse BinaryWriter e sovrascrive il metodo Dispose per impedire la chiusura del flusso figlio

Solo per aggiungerlo qui, una soluzione molto semplice sarebbe non eliminare Dispose () lo scrittore.

void R(MemoryStream M)
{
    B = new BinaryWriter(M);

    // write some stuff using B        
    B.Flush();
    S(M);  // now pass M to another routine for further processing
}

Ora devi solo preoccuparti di mantenere B nell'ambito, che sarà durante R ().

Questa potrebbe non essere la soluzione migliore qui, ma vale la pena notare che i lettori e gli scrittori non hanno bisogno di smaltirsi.

Un approccio un po 'ingenuo è usare

byte buf[] = MemoryStream.ToArray();

Per copiare il contenuto del flusso in un array di byte. Puoi trasformarlo in uno stream con

MemoryStream ms = new MemoryStream(buf);

Accedere a this M.Clone (); dovrebbe funzionare. Ma potrei sbagliarmi ...

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top