简体   繁体   English

如何一次遍历100个记录的数据集? C#

[英]How can I loop through a dataset 100 hundred records at a time? C#

I have a dataset that was roughly 4500 rows. 我的数据集大约有4500行。 I was passing it to a webservice but after performance issues and timeouts we want to be able to pass 100 of those rows at a time. 我将其传递给Web服务,但是在出现性能问题和超时之后,我们希望能够一次传递100行。

How can this be achieved in c#? 如何在C#中实现?

Do I need to split the dataset into tables of 100 and then loop through the tables or is there an easier way to send sets of 100 rows at a time? 我是否需要将数据集拆分为100个表,然后遍历这些表,还是有一种更简单的方式一次发送100行的集合?

You could use Linq, specifically Take and the CopyToDataTable extension. 您可以使用Linq,特别是TakeCopyToDataTable扩展。

Example: 例:

    DataSet ds = new DataSet();
    DataTable dt = ds.Tables["YOURDATATABLE"];
    IEnumerable<DataRow> firstHundred = dt.AsEnumerable().Take(100);
    // create datatable from query
    DataTable boundTable = firstHundred.CopyToDataTable<DataRow>();
    //call your web service with 1st hundred
    //
    IEnumerable<DataRow> nextHundred = dt.AsEnumerable().Skip(100).Take(100);
    // and so on
    boundTable = nextHundred.CopyToDataTable<DataRow>();
    //call your web service with 1st hundred
    //

Example with simple for and Linq which takes into account you have 4,500 rows and want to chunk it by groups of 100: 简单的for和Linq的示例考虑到您有4,500行,并希望按100组对它进行分块:

    DataSet ds = new DataSet();
    DataTable dt = ds.Tables["YOURDATATABLE"];
    IEnumerable<DataRow> firstHundred = dt.AsEnumerable().Take(100);
    // create datatable from query
    DataTable boundTable = firstHundred.CopyToDataTable<DataRow>();
    //call your web service with 1st hundred
    //

    int skipCount = 0;

    for (int i = 1; i <= 45; i++)
    {
        skipCount += 100;
        IEnumerable<DataRow> nextHundred = dt.AsEnumerable().Skip(skipCount).Take(100);
        // create datatable from query
        DataTable boundTable = nextHundred.CopyToDataTable<DataRow>();
        // call web service with next hundred and so on
    }
private IEnumerable<IEnumerable<DataRow>> GetChunks(DataTable table, int size)
{
    List<DataRow> chunk = new List<DataRow>(size);

    foreach (DataRow row in table.Rows)
    {
        chunk.Add(row);
        if (chunk.Count == size)
        {
            yield return chunk;
            chunk = new List<DataRow>(size);
        }
    }

    if(chunk.Any()) yield return chunk;
}

//....

DataTable table = dataSet.Tables[yourTable];
var chunks = GetChunks(table, 100);

foreach (IEnumerable<DataRow> chunk in chunks)
    SendChunk(chunk); // <-- Send your chunk of DataRow to webservice

You can also attempt to send the data on parallel: 您也可以尝试并行发送数据:

// This would replace the above last two lines
Parallel.ForEach(chunks, chunk => SendChunk(chunk));

Although I'd not recomment that, since SendChunk is an I/O operation. 尽管我不建议这样做,但因为SendChunk是I / O操作。

Instead, try to convert your code to async , and you can get better results: 相反,尝试将您的代码转换为async ,您可以获得更好的结果:

// Will execute all tasks at the same time
// SendChunk should return a Task
await Task.WhenAll(chunks.Select(chunk => SendChunk(chunk)).ToArray());

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM