SQL Server 使用C# .Net在.NET中对包含数千条记录的DataTable进行排序

gk7wooem  于 2023-01-20  发布在  C#
关注(0)|答案(1)|浏览(155)

我正在运行一个非常密集的数据查询(因此超时时间很长),但我想知道如何正确地对DataTable进行排序。
我的代码是这样开始的:

SqlDataAdapter da = new SqlDataAdapter();

SqlCommand command = new SqlCommand(sql, conn);
command.CommandTimeout = 36000;

da.SelectCommand = command;

DataTable dt = new DataTable();
da.Fill(dt);

DataView dv = new DataView(dt);

// Sorting
dv.Sort = "theId DESC";

int i = 0;

while (dt.Rows.Count > 0 && i < 5)
{
    DataRow row = dt.Rows[i];
    string theId = row["theId"].ToString();
    i++;
}

theId有大约2,000条记录,这些记录从1到2,000按数字顺序排列。
警告或不在SQL中使用ORDER BY是由于以下异常:
错误:发生异常
查询处理器无法生成查询计划,原因是需要工作表,并且工作表的最小行大小超过了允许的最大值8060字节,等等。
由于最大列大小为1,024,我也无法动态创建#TempTable
以某种方式编写查询的原因是由于系统和网络的限制,不能进行调整,也不能在本地运行查询。
我如何让排序后的DataTable工作,因为它需要传递给下一个函数,而由于它是对另一个系统的API调用,所以也不在我的控制范围内?

rpppsulh

rpppsulh1#

你不能真正对DataTable进行排序。你可以通过DataView来排序,就像你已经做过的那样,但是这只对视图排序,而不是对表排序。如果你随后通过Rows集合访问数据,你将看不到排序。你必须通过DataView访问数据。
实际上没有必要显式地创建DataView。每个DataTable在其DefaultView属性中都已经有了DataView。当你在WinForms中绑定一个DataTable时,显示的数据就来自那里。这就是你如何在DataGridView中或通过BindingSource对数据进行排序的方法。
当你使用Rows集合时,你会得到DataRow对象。当你使用DefaultView时,你会得到DataRowView对象。它们在很多方面都很相似,但也有一些区别。如果你只是想要数据,你可以使用列名索引并得到值。如果您通过DefaultView访问数据,但出于某种原因需要DataRow,则可以通过DataRowViewRow属性访问它。请尝试以下代码,了解它的工作原理:

var table = new DataTable();

table.Columns.Add("Name", typeof(string));

table.Rows.Add("Peter");
table.Rows.Add("Paul");
table.Rows.Add("Mary");

Console.WriteLine("Rows, unsorted");

foreach (DataRow row in table.Rows)
{
    Console.WriteLine(row["Name"]);
}

Console.WriteLine("DefaultView, unsorted");

foreach (DataRowView rowView in table.DefaultView)
{
    Console.WriteLine(rowView["Name"]);
}

table.DefaultView.Sort = "Name";

Console.WriteLine("Rows, sorted");

foreach (DataRow row in table.Rows)
{
    Console.WriteLine(row["Name"]);
}

Console.WriteLine("DefaultView, sorted");

foreach (DataRowView rowView in table.DefaultView)
{
    Console.WriteLine(rowView["Name"]);
}

Console.WriteLine("DefaultView to DataRow, sorted");

foreach (DataRowView rowView in table.DefaultView)
{
    Console.WriteLine(rowView.Row.Field<string>("Name"));
}

您可以从中看到,Rows集合中的数据在排序前后是相同的,而DefaultView以指定的顺序显示数据。最后一个循环显示了如何从DataRowViews访问DataRows,然后在DataRowViews不能使用的地方使用它们,例如,在LINQ to DataSet方法中。
请注意,如果确实需要对DataTable本身进行排序,则可以在DataView上调用ToTable以生成新的DataTable。新表将包含基于DataViewSortRowFilter属性的数据,如果需要,还可以省略某些列。您还可以指定只包括非重复记录。

相关问题