b2L*_*ord 4 .net c# ienumerable extension-methods
我需要在任何像这样的IDataReader实现上使用Linq
var c = sqlDataReader.AsEnumerable().Count();
Run Code Online (Sandbox Code Playgroud)
例:
public abstract class Test
{
public abstract SqlDataReader GetSqlDataReader();
public void Foo()
{
SqlDataReader sqlDataReader = GetSqlDataReader();
IEnumerable<SqlDataReader> sqlEnumerable = sqlDataReader.AsEnumerable();
var c = sqlEnumerable.Count();
var s = sqlEnumerable.Sum();
SqlDataReader first = sqlEnumerable.First();
var t = first.GetSqlXml(10);
}
}
Run Code Online (Sandbox Code Playgroud)
写这个的最好方法是什么.请写下你的代码片段.
Ser*_*rge 15
你可以用这个:
MyDataReader.Cast<IDataRecord>()
Run Code Online (Sandbox Code Playgroud)
但是在关闭DataReader之前不要忘记执行linq语句.
例如,使用ToList()
您可以创建一个扩展方法来执行此操作(请参阅下面的警告):
public static class DataReaderExtension
{
public static IEnumerable<Object[]> AsEnumerable(this System.Data.IDataReader source)
{
if (source == null)
throw new ArgumentNullException("source");
while (source.Read())
{
Object[] row = new Object[source.FieldCount];
source.GetValues(row);
yield return row;
}
}
}
Run Code Online (Sandbox Code Playgroud)
在这里找到:http://www.thinqlinq.com/default/Consuming-a ChallReader-with- LINQ.aspx
正如@LukeH指出的那样,请注意,由于IDataReader仅支持一次转发,因此您只能查询一次可枚举数.(为了解决这个问题,你可以调用ToList/ToArray,然后查询).
请注意,SqlDataReader已经暗示IEnumerable,因此您不需要在您给出的示例中执行此操作.
另外,请注意,在服务器上进行任何过滤/聚合可能更好(例如,通过LINQ to SQL)
试试这个:
public static class DataReaderExtension
{
public class EnumeratorWrapper<T>
{
private readonly Func<bool> moveNext;
private readonly Func<T> current;
public EnumeratorWrapper(Func<bool> moveNext, Func<T> current)
{
this.moveNext = moveNext;
this.current = current;
}
public EnumeratorWrapper<T> GetEnumerator()
{
return this;
}
public bool MoveNext()
{
return moveNext();
}
public T Current
{
get { return current(); }
}
}
private static IEnumerable<T> BuildEnumerable<T>(
Func<bool> moveNext, Func<T> current)
{
var po = new EnumeratorWrapper<T>(moveNext, current);
foreach (var s in po)
yield return s;
}
public static IEnumerable<T> AsEnumerable<T>(this T source) where T : IDataReader
{
return BuildEnumerable(source.Read, () => source);
}
}
Run Code Online (Sandbox Code Playgroud)
小智 6
您可以将其加载DataReader到 a 中DataTable,然后Select():
DataTable dt = new DataTable();
dt.Load(dataReader);
DataRow[] rows = dt.Select(); //DataRow[] Implements IEnumerable
Run Code Online (Sandbox Code Playgroud)
或者
IEnumerable<DataRow> rows = dt.AsEnumerable();
Run Code Online (Sandbox Code Playgroud)
这是我的两分钱:
public static IEnumerable<T> Enumerate<T>(this T reader) where T: IDataReader
{
using(reader)
while(reader.Read())
yield return reader;
}
public void Test()
{
var Res =
from Dr in MyDataReader.Enumerate()
select new {
ID = (Guid)Dr["ID"],
Description = Dr["Desc"] as string
};
}
Run Code Online (Sandbox Code Playgroud)
我强烈希望发布此内容,因为处理完DataReader售后使用非常重要,没有答案提及它。
这就是为什么我的实现using在while循环中有一条语句。通过这种方式,我可以进行“单手”查询,而不必担心如何DataReader处理。