C#如何将System.Net.ConnectStream转换为byte[]数组?

5

我想把一个流(System.Net.ConnectStream)转换成字节数组。有什么想法/示例可以做到这一点吗?


3
只需将其读入缓冲区(byte[])中。请参考 MSDN 上的 Stream.Read - Oded
@Oded,是的,但复制流的整个内容并不是一种非常简单的方法(除非您知道其长度,而在ConnectStream中并不总是这种情况)。 - Thomas Levesque
3个回答

14
Stream sourceStream = ... // the ConnectStream
byte[] array;
using (var ms = new MemoryStream())
{
    sourceStream.CopyTo(ms);
    array = ms.ToArray();
}

在这种情况下,您使用的内存是流的3倍。如果您的流可以占用比计算机更多的内存,则不太好。在这种情况下,您需要使用Stream.Read从源流中读取数据块并处理这些块。 - Kirill Bestemyanov
请注意,Stream.CopyTo 仅适用于 .NET 4.0 及以上版本。有关 4.0 之前版本的内容,请参阅 Kevin 的答案。 - Scott Chamberlain

4

试试这个...

    private static readonly object _lock = new object();

    public static byte[] readFullStream(Stream st)
    {
        try
        {
            Monitor.Enter(_lock);
            byte[] buffer = new byte[65536];
            Int32 bytesRead;
            MemoryStream ms = new MemoryStream();
            bool finished = false;
            while (!finished)
            {
                bytesRead = st.Read(buffer.Value, 0, buffer.Length);
                if (bytesRead > 0)
                {
                    ms.Write(buffer.Value, 0, bytesRead);
                }
                else
                {
                    finished = true;
                }
            }
            return ms.ToArray();
        }
        finally
        {
            Monitor.Exit(_lock);
        }
    }

1
这里有一个提示,如果你正在使用一个圆整的数字缓冲区(比如你的例子中的64k),你可以用64 << 10替换65536,其中左边是你的数字,右边是0 = 字节,10 = 千字节,20 = 兆字节,30 = 吉字节等...所以一个2MB的缓冲区将会是2 << 20 - Scott Chamberlain
另外,为什么你要在_lock上加锁?如果你想要独占地访问流,你应该在与流相关的某个对象上加锁(或在传入之前调用Stream.Synchronized)。你的代码中没有任何会因为同时处理两个不同的流而出错的情况。 - Scott Chamberlain

0

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接