将List添加到List 作为IList抛出exception

使用.NET 3.5和C#3.0,

IList list = new List(); list.Add(null); 

抛出一个ArgumentException,只是感觉不对。

 List list = new List(); list.Add(null); 

完美的工作。

这是微软代码中的错误吗?

在现实生活中如何产生这种错误的一个例子:

 new JavaScriptSerializer().Deserialize<List>("[true, false, null]"); 

是的。 有关其他报告,请参见http://social.msdn.microsoft.com/Forums/en-US/netfxbcl/thread/abc99fb5-e218-4efa-8969-3d96f6021cee/ 。 基本上当你通过它的弱类型IList实现访问List ,它会在尝试将项添加到内部存储之前进行一些类型检查 – 并且它会为可空类型检查此类型是否错误。

这是“按设计”而且明确如此。 原因是List具有IList的显式实现。 它过滤传递给各种方法的值,以进行一些空检查。 逻辑基本上如下

 if (default(T) != null && value == null) { throw ... } 

在这种情况下,值类型的默认值(并且可以为nullable是值类型)不为null,因此不允许。

哈! 那是一个有趣的。 我认为它与可疑的bool严格来说是作为结构实现的想法有关,而IList期望一个对象,也许它期望包装bool或其他东西。 Jon Skeet你在哪里? 我们需要你! (点击ruby拖鞋3次)

当您使用空值在IList上调用Add方法时,它是您传递给方法的空引用,而不是可空值。 无法将null引用转换为可空值。

Add方法需要包含boolbool? 。 由于无法装入空值,因此无法创建可用于向IList添加空值的对象。

如果您使用通用接口IList ,则添加值没有问题:

 IList list = new List(); list.Add(null); 

正如已经指出的那样,.NET 3.5中的List 类中的IList.Add(对象项)方法的实现存在一个错误(可能之前)。 问题是,IList.Add(对象项)方法试图validation我们尝试添加的对象是与List generics类型参数兼容的对象,当我们尝试添加null时失败到可空值类型列表。

我的解决方法涉及通过从List对象获取和调用Add(T item)方法来进行reflection。

 IList list = new List(); MethodInfo addMethod = list.GetType().GetMethod("Add"); addMethod.Invoke(list, new object[] { null }); 

您正在将通用List与非通用IListListinheritance自IList而不是IList