我在以下代码中收到警告CA2202(对象可以多次丢弃):
using (Stream responseStream = response.GetResponseStream())
{
if (responseStream != null)
using (var br = new BinaryReader(responseStream))
{
responseValue = br.ReadBytes(500000);
}
}
看起来,在调用BinaryReaders Dispose时会调用responseStreams Dispose。 BinaryReader是否始终调用Streams Dispose方法?
一种解决方案是直接初始化ResponseStream并让BinaryReader负责处理流(当然,如果BinaryReader在任何情况下都会处理流,那么它只会起作用)
Stream responseStream = response.GetResponseStream();
if(responseStream != null)
using (var br = new BinaryReader(responseStream)) //Always disposes the response stream?
[...]
我可以使用try / finalize而不是外部using语句来得到这样的东西:
Stream responseStream = null;
try
{
responseStream = response.GetResponseStream();
if (responseStream != null)
using (var br = new BinaryReader(responseStream))
{
responseValue = br.ReadBytes(500000);
}
}
finally
{
if(stream != null)
stream.Dispose;
}
当BinaryReader始终处理流时,这看起来不太好并且不必要。有没有更好/首选的解决方案来解决这类问题?
答案 0 :(得分:3)
如果您在VS 4.5中使用VS 2012,则可以创建不会关闭流的BinaryReader。 E.g:
using(var reader = new BinaryReader(theStream, new UTF8Encoding(), true)
{
//...
}
如果您使用BinaryReader(Stream)构造函数,则新的UTF8Encoding是默认值,如果您不想使用UTF8Encoding,则可以使用其他内容。真实表示“是的,让流开放”。
构造如:
public BinaryReader(
Stream input,
Encoding encoding,
bool leaveOpen
)
希望这会引导您找到您想要的东西。 欢呼声。
答案 1 :(得分:3)
您实际上可以了解BinaryReader.Dispose
的实施方式:
protected virtual void Dispose(bool disposing) {
if (disposing) {
Stream copyOfStream = m_stream;
m_stream = null;
if (copyOfStream != null && !m_leaveOpen)
copyOfStream.Close();
}
m_stream = null;
m_buffer = null;
m_decoder = null;
m_charBytes = null;
m_singleChar = null;
m_charBuffer = null;
}
public void Dispose()
{
Dispose(true);
}
现在,问题是,m_leaveOpen
是什么?这是一个标志,说明是否应该处理基础流!它默认设置为false
,这意味着将处理基础流:
public BinaryReader(Stream input) : this(input, new UTF8Encoding(), false) {
}
public BinaryReader(Stream input, Encoding encoding) : this(input, encoding, false) {
}
public BinaryReader(Stream input, Encoding encoding, bool leaveOpen) {
// (...)
m_leaveOpen = leaveOpen;
// (...)
}
因此,您可以跳过流式传输的using
语句,因为它将被处理:
responseStream = response.GetResponseStream();
if (responseStream != null)
{
using (var br = new BinaryReader(responseStream))
{
responseValue = br.ReadBytes(500000);
}
}
或只是
using (var br = new BinaryReader(response.GetResponseStream()))
{
responseValue = br.ReadBytes(500000);
}