我正在尝试获取LINQ查询返回的项目的计数。我认为它是.Count但显然不是。
我从Excel加载DataTable然后根据标识符获取不同的行。我现在正在尝试计算返回的项目。 Leases
包含我想要计数的行的数据。我尝试了一些事情(现已注释掉),但都没有成功。
也许LINQ专家可以帮助我?
这是我的代码:
Dim Leases As Object
Dim dtData As System.Data.DataTable = LoadExcelAsDb(oFile.FullName)
Try
' How many leases are there
Leases = From row In dtData.AsEnumerable() Select row.Field(Of Object)("F2") Distinct
' LeaseCt = New System.Linq.SystemCore_EnumerableDebugView(Of Object)(Leases).Items.count
' LeaseCt = New System.Linq.Enumerable(Of Object)(Leases).Items.count
' LeaseCt = Leases.Count
Catch ex As Exception
Debug.WriteLine("Error reading files" + ex.ToString)
End Try
''' <summary>
''' Loads an excel file as a datatable
''' </summary>
''' <param name="sFilename">Filename of excel to be loaded </param>
''' <returns>Populated Datatable</returns>
Private Function LoadExcelAsDb(sFilename As String) As System.Data.DataTable
' Connect to Excel get table
Dim oConnection As System.Data.OleDb.OleDbConnection = New System.Data.OleDb.OleDbConnection("provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + sFilename + " ; Extended Properties=Excel 12.0;")
Dim oCommand As System.Data.OleDb.OleDbDataAdapter = New System.Data.OleDb.OleDbDataAdapter("select * from [Sheet1$]", oConnection)
Dim DtSet As System.Data.DataTable = New System.Data.DataTable
Try
oCommand.Fill(DtSet)
Catch ex As Exception
Debug.WriteLine("Error reading files" + ex.ToString)
End Try
Return DtSet
End Function
答案 0 :(得分:1)
通常,使用ADO.NET和Linq的DataTable对于通常类似于List(Of(PocoObject))的较新类型的结构不能很好地发挥作用。然而,通常你可以通过以下方式欺骗它:
Sub Main()
Dim dt As DataTable = New DataTable()
dt.Columns.Add(New DataColumn("Id", GetType(Integer)))
Dim row As DataRow = dt.NewRow()
row("Id") = 1
dt.Rows.Add(row)
Dim row2 As DataRow = dt.NewRow()
row2("Id") = 2
dt.Rows.Add(row2)
'Shows 2 rows
Console.WriteLine(dt.Select().ToList().Count)
Console.ReadLine()
End Sub
密钥是DataTable没有&#39; ToList()&#39;延期,直到你选择&#39;它的东西。与Linq恕我直言的DataTable就像在高速公路上以错误的方式驾驶汽车。因为没有什么是好的类型,并且作为一些生产代码的例子,我必须从“数据集”中获得一些东西。我有一个WinForm解决方案然后只是将一组特定的列输出到POCO对象来制作列表我必须做这样的事情:
Dim ls = ds.Tables("tProduct").Select().Select(Function(x) New Product With {.ProductID = CInt(x("ProductId")?.ToString), .ProductDesc = x("ProductName")?.ToString}).ToList()
有趣的东西。注意双精选(),这不是拼写错误。一个是System.Data.DataTable的扩展,一个来自System.Linq.Enumerable。所以你需要选择才能选择lol。
答案 1 :(得分:1)
使用LINQ时需要掌握的一个主要概念是被查询的对象必须是可枚举的。这意味着它至少实现了接口System.Collections.IEnumerable。优选地,查询的对象将实现System.Collections.Generic.IEnumerable(Of T)接口。
在LINQ语句中:
Leases = From row In dtData.AsEnumerable() Select row.Field(Of Object)("F2") Distinct
查询的对象是结果dtData.AsEnumerable()
。 Datatable扩展方法AsEnumerable
返回System.Data.EnnumerableRowCollection(Of System.Data.DataRow),因此语句中的row
变量的类型为DataRow
。
语句选择 row.Field(Of Object)("F2")
。由于这将返回System.Object类型的单个对象,因此查询结果将为System.Collections.Generic.IEnumerable(Of Object)
类型。但是,您要将结果分配给以这种方式定义的变量Leases
:
Dim Leases As Object
对于以这种方式声明的变量,你无能为力。如果您将其声明为查询返回的类型会更好。
Dim Leases As System.Collections.Generic.IEnumerable(Of Object)
。
以这种方式定义,Leases
可以通过System.Linq.Enumerable类中声明的方法进行扩展,以允许调用Count扩展方法。