4

我有一个包含大约 50,000 行的 DataTable,用于DataTable.Select从中检索行。Select需要多个条件,AND包括通配符匹配。我玩过,发现通过Select多步执行相同的操作,可以大大减少执行时间,但更改AND语句的顺序并不会影响它。

//This takes ~ 750 ms
DataRow[] results = myDataTable.Select("Field1 LIKE '*" + term1 + "*'" +
"AND Field2 = '" + term2 + "'" +
"AND Field3 = '" + term3 + "'");

//This also takes ~750 ms
DataRow[] results2 = myDataTable.Select("Field3 = '" + term3 + "'" +
"AND Field2 = '" + term2 + "'" +
"AND Field1 LIKE '*" + term1 + "*'");  

//This takes 0.415 ms
DataTable table1 = myDataTable.Select("Field3 = '" + term3+ "'").CopyToDataTable();
DataTable table2 = table1.Select("Field2 = '" + term2 + "'").CopyToDataTable();
DataRow [] results3 = table2.Select("Field1 LIKE '*" + term1 + "*'");  

我的问题是,有没有办法总是让操作以从左到右的顺序SELECT评估条件,以便在步骤之间减少搜索的记录数?AND看起来这可能是一个很好的节省时间的方法。谢谢你的想法。

4

2 回答 2

5

您可以使用Linq(请注意,最慢的条件是最后一个):

IEnumerable<DataRow> rows = myDataTable.AsEnumerable()
    .Where(r => r.Field<string>("Field2") == term2
            &&  r.Field<string>("Field3") == term3
            &&  r.Field<string>("Field1").Contains(term1));

如果CopyToDataTable您想从结果中创建一个新的 DataTable,请使用它ToArray来创建DataRow[]或保留它并用于foreach枚举结果而不创建新集合。

于 2013-04-25T16:06:27.973 回答
1

不..数据表逐行进行选择。

你可以把你的代码写得更短一点:

DataRow [] results = myDataTable
     .Select("Field3 = '" + term3+ "'").CopyToDataTable()
     .Select("Field2 = '" + term2 + "'").CopyToDataTable()
     .Select("Field1 LIKE '*" + term1 + "*'");

或者......如果你做一个额外的扩展方法,像这样:

static public DataRow[] Select(this IEnumerable rows, string filter) { return rows.CopyToDataTable().Select(filter); }

使用这个扩展可以让你的代码更短:

DataRow [] results = myDataTable
     .Select("Field3 = '" + term3+ "'")
     .Select("Field2 = '" + term2 + "'")
     .Select("Field1 LIKE '*" + term1 + "*'");

或者:

static public DataRow[] Select(this DataTable dt, string firstFilter, params string[] filters)
{
    DataRow[] result = dt.Select(firstFilter);
    foreach(string filter in filters)
        result = result.CopyToDataTable().Select(filter);
    return result;
}

开辟道路:

DataRow [] results = myDataTable.Select(
    "Field3 = '" + term3+ "'", 
    "Field2 = '" + term2 + "'",
    "Field1 LIKE '*" + term1 + "*'");
于 2013-04-25T16:06:03.147 回答