数据表选择同一列上的linq查询,具有两个不同的条件,从而产生零行

时间:2013-05-23 08:16:03

标签: c#

IEnumerable<DataRow> mergedRows = from myRow in _gridData.AsEnumerable()
                                              select myRow;

IEnumerable<DataRow> rows;

rows = from myRow in mergedRows where  
double.Parse(myRow["signalName"].ToString())> 1800 &&
                                       select myRow;

mergedRows = rows;
IEnumerable<DataRow> rows;//reinitializing 
rows = from myRow in mergedRows where
double.Parse(myRow["signalName"].ToString()) < 2400
                                       select myRow;

上面的一个给我零结果,这是错误的.. 当查询运行第二次时,mergedRows在第一个条件之后有结果数据。在第二次查询执行后,我仍然没有得到结果。

但是使用组合条件的相同查询工作正常。

IEnumerable<DataRow> mergedRows = from myRow in _gridData.AsEnumerable()
                                              select myRow;
IEnumerable<DataRow> rows;

rows = from myRow in mergedRows  where 
double.Parse(myRow[signalName].ToString()) > 1800 &&
double.Parse(myRow[signalName].ToString()) < 2400
                                       select myRow;

这个给我的确切结果是正确的。

你能解释一下为什么......

1 个答案:

答案 0 :(得分:1)

我想你可能会遇到一个&#34; deferred execution&#34;问题

这包含您的&#34;来源&#34;数据

 IEnumerable<DataRow> mergedRows = from myRow in _gridData.AsEnumerable()
                                          select myRow;

这包含您的查询但尚未实际执行。

IEnumerable<DataRow> rows = from myRow in mergedRows where  
                            double.Parse(myRow["signalName"].ToString())> 1800 
                            select myRow;

然后用未执行的查询覆盖您的源数据

mergedRows = rows;

您可以尝试通过将查询包装在.ToList();

中来贪婪地执行查询
IEnumerable<DataRow> mergedRows = from myRow in _gridData.AsEnumerable()
                                              select myRow;

var rows = (from myRow in mergedRows where  
            double.Parse(myRow["signalName"].ToString())> 1800 &&
            select myRow).ToList();

mergedRows = rows;


rows = (from myRow in mergedRows where
        double.Parse(myRow["signalName"].ToString()) < 2400
        select myRow).ToList();

如果你总是要执行这两个过滤器,我会考虑清理整个过程并将所有工作合并到一个查询中。

private double SafeParse(string s)
{
    double d;
    return double.TryParse(s, out d) ? d : 0; //return zero if the value is unparsable
}


var results = (from myRow in _gridData.AsEnumerable()
              let d = SafeParse(myRow[signalName].ToString()) 
              where d > 1800 && d < 2400
              select myRow).ToList();