有人找到/编码了批量查询数据(使用linq to sql)的扩展方法吗?我见过 IEnumerable 扩展,但我正在寻找我可能会使用的东西,如下所示:
IQueryable<Order> orders = from i in db.Orders select i;
foreach(var batch in orders.InBatches(100))
{
//batch of 100 products
foreach(var order in batch)
{
//do something
}
}
你能做的是:
public static IEnumerable<T[]> InBatches<T>(this IQueryable<T> collection, int size)
{
List<T> batch = new List<T>(size);
foreach (T item in collection)
{
if (batch.Count == size)
{
yield return batch.ToArray();
batch.Clear();
}
batch.Add(item);
}
if (batch.Count > 0) yield return batch.ToArray();
}
此扩展方法循环遍历 IQueryable 一次(即对数据库的一次查询),并以流方式将批次吐出为数组。通过流式传输结果,它只允许将数据的子集保留在内存中(这对于非常大的数据集来说很有趣)。
用途:
IQueryable<Order> orders = from order in db.Orders select order;
foreach (Order[] batch in orders.InBatches(size: 100))
{
// Batch of 100 products
foreach(Order order in batch)
{
//do something
}
}
如果您不关心批次本身,而只想出于大小或事务目的断开连接,则可以执行以下操作:
public static IEnumerable<T> InBatches<T>(this IQueryable<T> collection, int batchSize)
{
int start = 0;
int records = 0;
IQueryable<T> batch;
// For the first batch
start -= batchSize;
do {
records = 0;
start += batchSize;
batch = collection.Skip(start).Take(batchSize);
foreach (T item in batch) {
records += 1;
yield return item;
}
} while (records == batchSize);
}