gpt4 book ai didi

c# - 从 SQL Server 检索 blob 数据的最有效内存方式

转载 作者:太空宇宙 更新时间:2023-11-03 10:59:23 24 4
gpt4 key购买 nike

从 SQL Server 检索大型 blob 数据时出现内存不足异常。我正在调用一个存储过程,它返回 6 列简单数据和 1 个 varbinary(max) 数据列。

我正在使用这段代码来执行存储过程:

m_DataReader = cmd.ExecuteReader(CommandBehavior.SequentialAccess);

并确保我按顺序列顺序从数据读取器读取列。

参见 MSDN article on retrieving large data

对于 varbinary(max) 列,我是这样读取数据的:

DocBytes = m_DataReader.GetValue(i) as byte[];

我注意到,在内存不足时,内存中似乎有 2 个字节数组副本。一个在 DocBytes 数组中,另一个在 SqlDataReader 的内部缓冲区中。

为什么会有这个副本?我假设我会传递一个引用,或者这是由于 SqlDataReader 提供数据的内部方式 - 即它总是提供一个副本?

是否有一种内存效率更高的方式从数据库中读取数据?

我看过新的 .NET 4.5 GetStream方法,但不幸的是,我没有能力传递流 - 我需要内存中的字节 - 所以我无法按照流式传输到文件或 Web 响应的其他示例进行操作。但我想尝试确保内存中一次只存在一个副本!

我得出的结论是,这可能只是必须的方式,重复副本只是一个尚未被垃圾收集的缓冲区。我真的不想为强制垃圾收集而烦恼,我希望有人对替代方法有一些想法。

最佳答案

问题在于 DbDataReader.GetStream() 创建了一个 MemoryStream 并用该字段的数据填充该流。为了避免这种情况,我创建了一个扩展方法:

public static class DataReaderExtensions
{
/// <summary>
/// writes the content of the field into a stream
/// </summary>
/// <param name="reader"></param>
/// <param name="ordinal"></param>
/// <param name="stream"></param>
/// <returns>number of written bytes</returns>
public static long WriteToStream(this IDataReader reader, int ordinal, Stream stream)
{
if (stream == null)
throw new ArgumentNullException("stream");

if (reader.IsDBNull(ordinal))
return 0;

long num = 0L;
byte[] array = new byte[8192];
long bytes;
do
{
bytes = reader.GetBytes(ordinal, num, array, 0, array.Length);
stream.Write(array, 0, (int)bytes);
num += bytes;
}
while (bytes > 0L);
return num;
}

/// <summary>
/// writes the content of the field into a stream
/// </summary>
/// <param name="reader"></param>
/// <param name="field"></param>
/// <param name="stream"></param>
/// <returns>number of written bytes</returns>
public static long WriteToStream(this IDataReader reader, string field, Stream stream)
{
int ordinal = reader.GetOrdinal(field);
return WriteToStream(reader, ordinal, stream);
}
}

关于c# - 从 SQL Server 检索 blob 数据的最有效内存方式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18249648/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com