Tengo el siguiente método constructor que se abre un MemoryStream de una ruta de acceso de archivo:

MemoryStream _ms;

public MyClass(string filePath)
{
    byte[] docBytes = File.ReadAllBytes(filePath);
    _ms = new MemoryStream();
    _ms.Write(docBytes, 0, docBytes.Length);
}

Necesito cambiar esto para que acepte un Stream en lugar de una ruta de archivo. Cuál es la forma más fácil y más eficiente para llegar a un MemoryStream de la Stream objeto?

  • Una vez que usted tiene la Corriente, ¿por qué molestarse convertirlo a un MemoryStream? No puede trabajar con la Secuencia directamente?
  • Necesito un MemoryStream debido a otras dependencias.
  • También hay casos en que el mal rendimiento de trabajar con Secuencias de hace un MemoryStream a ser más eficientes. Como mi pregunta aquí: stackoverflow.com/questions/50399481/…

9 Comentarios

  1. 28

    Si usted está modificando su clase para que acepte un Flujo en lugar de un nombre de archivo, no te preocupes por la conversión a un MemoryStream. Deje que la Secuencia subyacente a manejar las operaciones:

    public class MyClass
    { 
        Stream _s;
    
        public MyClass(Stream s) { _s = s; }
    }

    Pero si usted realmente necesita un MemoryStream para las operaciones internas, tendrás que copiar los datos de la fuente de Corriente en la MemoryStream:

    public MyClass(Stream stream)
    {
        _ms = new MemoryStream();
        CopyStream(stream, _ms);
    }
    
    //Merged From linked CopyStream below and Jon Skeet's ReadFully example
    public static void CopyStream(Stream input, Stream output)
    {
        byte[] buffer = new byte[16*1024];
        int read;
        while((read = input.Read (buffer, 0, buffer.Length)) > 0)
        {
            output.Write (buffer, 0, read);
        }
    }
    • Estoy suponiendo que la > 0 al final de la mientras que la línea?
    • Correcto. Tengo un poco de eliminar feliz. Fijo.
    • se ve como un paréntesis de cierre es la que falta. debe ser while((read = input.Read(buffer,0,buffer.Length)) > 0)
    • Quizás desee agregar output.Position = 0; como la última línea de lo contrario deberás recordar para reiniciar más tarde.
  2. 179

    En .NET 4, puede utilizar Stream.CopyTo para copiar un arroyo, en vez de la casa de filtrado de los métodos mencionados en las otras respuestas.

    MemoryStream _ms;
    
    public MyClass(Stream sourceStream)
    
        _ms = new MemoryStream();
        sourceStream.CopyTo(_ms);
    }
    • Asegúrese de que el primer conjunto de sourceStream.Posición = 0;
    • Usted tendrá que configurar _ms.Posición = 0; antes de utilizarlo.
  3. 42

    Usar este:

    var memoryStream = new MemoryStream();
    stream.CopyTo(memoryStream);

    Esto convertirá Stream a MemoryStream.

  4. 3

    Usted tendrá que leer todos los datos de la Secuencia de objetos en un byte[] búfer y, a continuación, pasar a la MemoryStream a través de su constructor. Puede ser mejor, para ser más específicos sobre el tipo de objeto stream está utilizando. Stream es muy genérica y puede no aplicar la Length atributo, el cual es bastante útil cuando la lectura de los datos.

    Aquí un poco de código para usted:

    public MyClass(Stream inputStream) {
        byte[] inputBuffer = new byte[inputStream.Length];
        inputStream.Read(inputBuffer, 0, inputBuffer.Length);
    
        _ms = new MemoryStream(inputBuffer);
    }

    Si el Stream objeto de no aplicar el Length atributo, usted tendrá que implementar algo como esto:

    public MyClass(Stream inputStream) {
        MemoryStream outputStream = new MemoryStream();
    
        byte[] inputBuffer = new byte[65535];
        int readAmount;
        while((readAmount = inputStream.Read(inputBuffer, 0, inputBuffer.Length)) > 0)
            outputStream.Write(inputBuffer, 0, readAmount);
    
        _ms = outputStream;
    }
  5. 2

    Yo uso esta combinación de métodos de extensión:

        public static Stream Copy(this Stream source)
    {
    if (source == null)
    return null;
    long originalPosition = -1;
    if (source.CanSeek)
    originalPosition = source.Position;
    MemoryStream ms = new MemoryStream();
    try
    {
    Copy(source, ms);
    if (originalPosition > -1)
    ms.Seek(originalPosition, SeekOrigin.Begin);
    else
    ms.Seek(0, SeekOrigin.Begin);
    return ms;
    }
    catch
    {
    ms.Dispose();
    throw;
    }
    }
    public static void Copy(this Stream source, Stream target)
    {
    if (source == null)
    throw new ArgumentNullException("source");
    if (target == null)
    throw new ArgumentNullException("target");
    long originalSourcePosition = -1;
    int count = 0;
    byte[] buffer = new byte[0x1000];
    if (source.CanSeek)
    {
    originalSourcePosition = source.Position;
    source.Seek(0, SeekOrigin.Begin);
    }
    while ((count = source.Read(buffer, 0, buffer.Length)) > 0)
    target.Write(buffer, 0, count);
    if (originalSourcePosition > -1)
    {
    source.Seek(originalSourcePosition, SeekOrigin.Begin);
    }
    }
  6. 1
    public static void Do(Stream in)
    {
    _ms = new MemoryStream();
    byte[] buffer = new byte[65536];
    while ((int read = input.Read(buffer, 0, buffer.Length))>=0)
    _ms.Write (buffer, 0, read);
    }
  7. 0
    byte[] fileData = null;
    using (var binaryReader = new BinaryReader(Request.Files[0].InputStream))
    {
    fileData = binaryReader.ReadBytes(Request.Files[0].ContentLength);
    }
  8. 0

    Usted puede simplemente hacer:

    var ms = new MemoryStream(File.ReadAllBytes(filePath));

    Flujo de la posición es 0 y listo para usar.

Dejar respuesta

Please enter your comment!
Please enter your name here