我有一个针对数据库运行的查询,我可以看到有一个31/05/2013的记录。当我使用ADO.NET从C#运行此查询,然后使用以下代码时,我错过了31/05/2013的记录
var timeSeriesList = new List<TimeSeries>();
using (var reader = cmd.ExecuteReader())
{
while (reader.Read())
{
timeSeriesList = reader.Cast<IDataRecord>()
.Select(r => new TimeSeries
{
MidRate = (double)r["MidRate"],
RiskFactorName = (string)r["RiskFactorName"],
SeriesDate = (DateTime)r["SeriesDate"]
}).ToList();
}
}
但是,如果我对此代码使用相同的查询:
var timeSeriesList = new List<TimeSeries>();
using (var reader = cmd.ExecuteReader())
{
while (reader.Read())
{
var timeSeries = new TimeSeries
{
MidRate = (double)reader["MidRate"],
RiskFactorName = (string)reader["RiskFactorName"],
SeriesDate = (DateTime)reader["SeriesDate"]
};
timeSeriesList.Add(timeSeries);
}
}
...然后2013年5月31日的记录在集合中 - 为什么第一个代码块会给出这个结果?
答案 0 :(得分:6)
我认为您在第一个示例中缺少记录,因为您将读者移动一个然后再将其转换。
尝试此更改并查看其是否有效:
var timeSeries = new List<TimeSeries>();
using (var reader = cmd.ExecuteReader())
{
if (reader.HasRows)
{
timeSeries = reader.Cast<IDataRecord>()
.Select(r => new TimeSeries
{
MidRate = (double)r["MidRate"],
RiskFactorName = (string)r["RiskFactorName"],
SeriesDate = (DateTime)r["SeriesDate"]
}).ToList();
}
}
答案 1 :(得分:3)
有两种方法可以迭代数据读取器;一个是继续打电话.Read()
;另一种方法是将其视为IEnumerable
和IDataRecord
的{{1}}序列;无论你选择哪一个,你都只能迭代一次数据。
foreach
的调用从BOF移动到第一条记录(如果有)
.Read()
调用ToList()
然后调用GetEnumerator()
循环,立即前进一个位置(所以我们删除了第一个记录在地板上没有处理它);在MoveNext()
的末尾我们已经咀嚼了所有数据ToList()
将报告.Read()
(EOF)基本上:这里的问题是使用两个API来推进这个位置。使用false
,或使用.Read()
API(foreach
)。
作为旁注,由于列名与成员名相匹配,您还可以使用“dapper”来完成繁重的工作:
.ToList()