严格来说,这算是 C# 基础知识的一部分。不知是太久远我记不清了,还是这部分本来就没注意,最近发现了,不算坑,在这里写一下。

我们知道,不管是 String,还是 Dictionary,都没实现 IDisposable,所以这两个地方都是没法转换的。可是奇怪的是,编译时,disposable1 那一行会报 Error,而第二个转换则是运行时才会抛出异常。

我一开始以为是编译器特殊处理了一些内置类型,准备过会儿查查文档。

其中的讨论提醒了我。

我猛地想起刚才那个现象,像 String、Int32 这样的类型,要么是 sealed class,要么是 struct,都不可能有派生类了。这样,编译器完全可以在编译期就发现,这个转换没法进行,因为没有派生类可以再去实现接口了。

这段代码可以通过编译。然后把类加上 sealed。

在我查找的范围内,文档中对此现象的描述比较模糊,仅说显示转换可能失败,并在运行时抛出异常。