gpt4 book ai didi

c# - 为什么处置后的对象在使用它时不会抛出异常?

转载 作者:可可西里 更新时间:2023-11-01 07:51:04 26 4
gpt4 key购买 nike

在处置对象上调用方法是否合法?如果是,为什么?

在下面的演示程序中,我有一个一次性类 A(它实现了 IDisposable 接口(interface))。据我所知,如果我将一次性对象传递给 using() 构造,然后在右括号处自动调用 Dispose() 方法:

A a = new A();
using (a)
{
//...
}//<--------- a.Dispose() gets called here!

//here the object is supposed to be disposed,
//and shouldn't be used, as far as I understand.

如果正确,请解释这个程序的输出:

public class A : IDisposable
{
int i = 100;
public void Dispose()
{
Console.WriteLine("Dispose() called");
}
public void f()
{
Console.WriteLine("{0}", i); i *= 2;
}
}

public class Test
{
public static void Main()
{
A a = new A();
Console.WriteLine("Before using()");
a.f();
using ( a)
{
Console.WriteLine("Inside using()");
a.f();
}
Console.WriteLine("After using()");
a.f();
}
}

输出(ideone):

Before using()
100
Inside using()
200
Dispose() called
After using()
400

如何在处置对象 a 上调用 f()?这是允许的吗?如果是,那为什么?如果不是,那么为什么上面的程序在运行时没有给出异常?


我知道使用 using 的流行构造是这样的:

using (A a = new A())
{
//working with a
}

但我只是在试验,这就是我以不同方式编写的原因。

最佳答案

处置并不意味着消失。 Disposed 仅表示已释放任何非托管资源(如文件、任何类型的连接...)。虽然这通常意味着该对象不提供任何有用的功能,但可能仍有一些方法不依赖于该非托管资源并且仍然照常工作。

Disposing 机制作为 .net(以及继承的 C#.net)存在,是一个垃圾收集环境,这意味着您不负责内存管理。但是,垃圾收集器无法确定非托管资源是否已使用完毕,因此您需要自己执行此操作。

如果您希望方法在对象被处置后抛出异常,您需要一个 bool 值来捕获处置状态,一旦对象被处置,您就抛出异常:

public class A : IDisposable
{
int i = 100;
bool disposed = false;
public void Dispose()
{
disposed = true;
Console.WriteLine("Dispose() called");
}
public void f()
{
if(disposed)
throw new ObjectDisposedException();

Console.WriteLine("{0}", i); i *= 2;
}
}

关于c# - 为什么处置后的对象在使用它时不会抛出异常?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7456953/

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