简体   繁体   中英

How to Wait until all Items processed in a list using Async Await - c#

I am trying to achieve following functionality using this code

1. I have list of items and i want process items in parallel way to speed up the process.

2. Also i want to wait until all the data in the list get processed and same thing i need to update in database

   private async Task<bool> ProceeData<T>(IList<T> items,int typeId,Func<T, bool> updateRequestCheckPredicate, Func<T, bool> newRequestCheckPredicate)
    {
            continueFlag = (scripts.Count > =12 ) ? true : false;
            await ProcessItems(items, updateRequestCheckPredicate, newRequestCheckPredicate);

            //Wait Until all items get processed and Update Status in database

            var updateStatus =UpdateStatus(typeId,DateTime.Now);
             return continueFlag;
    }

    private async Task ProcessItems<T>(IList<T> items,Func<T, bool> updateRequestCheckPredicate, Func<T, bool> newRequestCheckPredicate)
    {
       var itemsToCreate = items.Where(newRequestCheckPredicate).ToList();

        var createTask  = scripts
                     .AsParallel().Select(item => CrateItem(item);
                     .ToArray();
        var createTaskComplete = await Task.WhenAll(createTask);

        var itemsToUpdate = items.Where(updateRequestCheckPredicate).ToList();

        var updateTask = scripts
                   .AsParallel().Select(item => UpdateItem(item)
                   .ToArray();

        var updateTaskComplete = await Task.WhenAll(updateTask);
    }

     private async Task<ResponseResult> CrateItem<T>(T item)
    {
        var response = new ResponseResult();
         Guid requestGuid = Guid.NewGuid();
        auditSave = SaveAuditData(requestGuid);
        if (auditSaveInfo.IsUpdate)
        {
           response = await UpdateItem(item);
        }
        response = await CreateTicket<T>(item);
        // Wait response
        UpdateAuditData(response)
    }
    private async Task<ServiceNowResponseResult> CreateTicket<T>(T item)
    {
        // Rest call and need to wait for result
        var response = await CreateNewTicket<T>(scriptObj, serviceRequestInfo);
        return response;
    }

I am new to await async concept and so anyone pls advice me whether i am doing is a right approach or If wrong pls help me with help of a sample code

All these AsParallel are not needed or desired, but you'd need to change the signature of your callbacks to be async.

Here's an example

    async Task ProcessAllItems<T>(IEnumerable<T> items,
        Func<T, Task<bool>> checkItem, // an async callback
        Func<T, Task> processItem)
    {
// if you want to group all the checkItem before any processItem is called
// then do WhenAll(items.Select(checkItem).ToList()) and inspect the result
// the code below executes all checkItem->processItem chains independently
        List<Task> checkTasks = items
            .Select(i => checkItem(i)  
            .ContinueWith(_ =>
            {
                if (_.Result)
                    return processItem(i);
                return null;
            }).Unwrap())   // .Unwrap takes the inner task of a Task<Task<>>
            .ToList();     // when making collections of tasks ALWAYS materialize with ToList or ToArray to avoid accudental multiple executions

        await Task.WhenAll(checkTasks);

    }

And here's how to use it:

var items = Enumerable.Range(0, 10).ToList();
var process = ProcessAllItems(items,
    checkItem: async (x) =>
    {
        await Task.Delay(5);
        return x % 2 == 0;
    },
    processItem: async (x) =>
    {
        await Task.Delay(1);
        Console.WriteLine(x);
    });

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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