Dispose 方法不允许对象参与 C# 中的使用.为什么?



Dispose 方法不允许对象参与 C# 中的使用。为什么?

根据通过 C# 的 CLR

如果动态表达式被指定为 foreach 语句中的集合或 使用 语句,编译器将生成尝试将表达式强制转换为 非通用 System.IEnumerable 接口或 System.IDisposable 接口。 如果强制转换成功,则使用表达式,代码运行良好。如果强制转换失败,则 Microsoft.CSharp.RuntimeBinder.RuntimeBinderException 被抛出。

因此,我正在尝试以下方法:

using System;
namespace myprogram
{
delegate void VoidRes();
class Program
{
static void Main(string[] args)
{
dynamic a = new
{
Dispose = new VoidRes
(
delegate () { Console.WriteLine("in Dispose"); }
)
};
using(a) {
Console.WriteLine("foo");
}
}
}
}

我收到一个错误:

未处理的异常。Microsoft.CSharp.RuntimeBinder.RuntimeBinderException:无法将类型"<>f__AnonymousType4"隐式转换为"System.IDisposable" at CallSite.Target(Closure , CallSite , Object ( at System.Dynamic.UpdateDelegates.UpdateAndExecute1[T0,TRet](CallSite site, T0 arg0(

这很奇怪,因为我认为为了满足IDisposable接口,实现Dispose方法就足够了(这正是我在匿名类型中所做的(。

我在这里错过了什么?

匿名类型不会仅仅因为它具有IDisposable接口具有的方法而实现IDisposable接口。匿名类型无法实现接口。看这里: https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/anonymous-types

其中指出:

"匿名类型是直接从对象派生的类类型,不能强制转换为对象以外的任何类型。">

实现IDisposable就足够了,但它没有发生在代码中的任何位置。C# 中的接口实现是通过创建类/结构并显式指示接口类型来完成的。对象具有相同的成员(属性、方法等(来匹配接口是不够的。(这种行为称为鸭子类型,存在于其他一些语言中。

即使在 C# 中可以进行鸭式键入,这种特殊情况仍然不起作用。这是因为new { Dispose = ... }创建了一个匿名类的实例,该实例具有一个名为Dispose的属性(而不是方法(。因此,不满足IDisposable接口的协定。

匿名类也不实现接口,特别是IDisposable

最新更新