2011-02-08 103 views
6

可能重复:
Why does var evaluate to System.Object in “foreach (var row in table.Rows)”?“VAR” 类型推断

我惊讶,而在今天下发现....

SqlDataReader reader = cmd.ExecuteReader(); 
DataTable schemaTable = reader.GetSchemaTable(); 


// the following compiles correctly 
foreach (DataRow field in schemaTable.Rows) 
{ 
    Console.WriteLine(field["ColumnName"]); 
} 


// the following does not compile as 'var' is of type 'object' 
foreach (var field in schemaTable.Rows) 
{ 
    // Error: Cannot apply indexing with [] to an expression of type 'object' 
    Console.WriteLine(field["ColumnName"]); 
} 

打算请告诉我在这?

这是一种类型推断失败?如果是这样,是什么原因造成的?

或者它是定义的行为的一部分或var?如果是这样,为什么?

我想到了var的想法是,你可以在一个变量声明/初始化任何地方使用它,而改变行为

+1

`DataRowCollection.GetEnumerator()`返回`IEnumerator`。 “IEnumerator.Current”的类型是“object”。 – 2011-02-08 13:47:28

+0

[确切的重复问题](http://stackoverflow.com/questions/2325777/why-cant-i-do-foreach-var-item-in-datatable-rows)基本上行是一个`DataRowCollection`,所以编译器拿起`对象`,而不是`DataRow` – Axarydax 2011-02-08 13:42:14

回答

3

这里的关键不是var,而是foreach循环。 foreach循环除了迭代本身外,还可以选择性地投射迭代器。

所以,你可以做到以下几点:

List<object> test = new List<object>(); 
test.Add(1); 
test.Add(2); 
test.Add(3); 
foreach(int i in test){ 
    i.Dump(); 
} 

因此,即使该列表类型的对象,它可以被铸造为int在里面的foreach飞。

0

令人困惑的是,foreach(SomeType thing in SomeCollection)不只是遍历集合,它还会在迭代时尝试为每个项目转换为SomeType。但是,var没有什么可以投入的。

1

DataTable.Rows返回System.Data.DataRowCollection它是InternalDataCollectionBase的子类。

GetEnumerator关于此的方法返回IEnumerator,而不是IEnumerator<DataRows>

因此,唯一可用的类型信息是它返回object,所以当您指定您正在枚举DataRow时,您正在添加自己的演员,而其中的var不会。