繁体   English   中英

为什么<enum>的集合无法转换为<int?>?

[英]Why is a collection of <enum> unable to cast to an <int?>?

为什么enum的集合无法转换为int?

enum Test { A = 1, B = 2 };

int? x = (int?)Test.A; // Valid

var collection1 = new[] { Test.A }.Cast<int>().ToList();

// InvalidCastException has thrown (Specified cast is not valid.)    
var collection2 = new[] { Test.A }.Cast<int?>().ToList(); 

Cast方法只能在枚举类型及其基础整数类型之间执行装箱/拆箱转换,引用转换和转换。 取消装箱必须是正确的类型 - 它不能取消装入可以为空的类型(与C#转换不同)。

var collection1 = new[] { Test.A }.Cast<int>()
                                  .Select(x => (int?) x)
                                  .ToList();

对于每个值, Cast会从盒装enum值中取消框到int值,然后Select会将int值转换为int? 值。

在这种情况下,你可以逃避:

var collection1 = new[] { Test.A }.Select(x => (int?) x)
                                  .ToList();

即没有Cast步骤。 但是,如果您有一个object数组, 不起作用:

// Fails
var collection1 = new object[] { Test.A }.Select(x => (int?) x)
                                         .ToList();

您不能将装箱的枚举值取消装入可以为空的int值。 然而,在这种情况下, Cast版本仍然适用,因为它拆分了两个步骤(首先拆箱为int ,然后从int转换为int?

这是因为内部的Cast()做了类似的事情:

object o = Test.A;

int i = (int)o; // This is valid.
int? ni = (int?)o; // This is not valid!

你必须首先将Cast()转换为int:

var collection3 = new[] { Test.A }.Cast<int>().ToList().Cast<int?>().ToList();

或者根本不使用Cast()

var collection4 = new object[] { Test.A, null }.Select(i => i == null ? null : (int?)(int)i).ToList();

它不起作用,因为我们需要了解什么是枚举和什么是int? (可以为空)

诠释? 是不是真的是一个int它是Nullable的通用实例, - 语法T? 是System.Nullable的简写,其中T是值类型。 这两种形式是可以互换的。 链接

枚举枚举元素的默认基础类型是int。 链接

因此,存在int和enum之间的隐式转换。 但是,enum(int)与Nullable(完全不同的引用类型)之间的隐式转换不存在。 这就是您看到InvalidCastException异常的原因。

在第一个int? x = (int?)Test.A; int? x = (int?)Test.A; 声明你强制显式转换为框的值类型并获得一个整数或获得一个null,这是有效的,因为将枚举装入object然后将其拆箱为int? 正在返回一个int。

我不知道为什么Cast<>()不起作用,但你可以使用Select()来做你想要的。

var collection = new[] { Test.A }.Select(item => (int?)item).ToList();

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM