将字节[]转换为图像而不使用MemoryStream

本文关键字:MemoryStream 图像 字节 转换 | 更新日期: 2023-09-27 18:13:06

我有一个问题,导出SQL图像到文件。我首先初始化一个List。MyRecord是一个具有GraphicName和Graphic属性的类。当我尝试浏览列表并保存MyRecord时。图形到磁盘我得到类型'System.ObjectDisposedException'的第一次机会异常。我意识到这是因为当我将字节从数据库转换为图像时,我使用使用语句与MemoryStream。我不能使用using语句,这一切都有效,但我担心内存使用/内存泄漏多达6000条记录。是否有另一种方法将字节转换为图像,或者是否有更好的设计来做到这一点?

... prior code
using (SqlDataReader reader = sqlCommand.ExecuteReader())
{
    while (reader.Read())
    {
        MyRecord record = new MyRecord();
        record.GraphicId = reader["GRAPHIC_ID"].ToString();
        record.Graphic = !reader.IsDBNull(reader.GetOrdinal("IMAGE")) ? GetImage((byte[])reader["IMAGE"]) : null;
        records.Add(record);
    }
... more code
private Image GetImage(byte[] rawImage)
{
    using (System.IO.MemoryStream ms = new System.IO.MemoryStream(rawImage))
    {
        Image image = Image.FromStream(ms);
        return image;
    }
}

将字节[]转换为图像而不使用MemoryStream

不应该使用将传递给Image.FromStream的流的using语句,因为Image类从那时起基本上负责流。来自文档:

必须在图像的生命周期内保持流打开。

把你的代码改成:

private Image GetImage(byte[] rawImage)
{
    var stream = new MemoryStream(rawImage);
    return Image.FromStream(stream);
}

…但要确保稍后处理掉Image对象。这将处理流,从而允许对内存进行垃圾收集。那么就不应该有任何内存泄漏——但是你需要弄清楚你是否真的可以一次将所有6000张图片加载到内存中。

(如果您不处理Image对象,它们很可能在某个时候最终确定-但最好是确定地处理它们。)