Csharp/C#教程:与WhenAll并行执行任务时的任务缓存分享


与WhenAll并行执行任务时的任务缓存

所以我有这个小代码块,可以并行执行几个任务。

// no wrapping in Task, it is async var activityList = await dataService.GetActivitiesAsync(); // Select a good enough tuple var results = (from activity in activityList select new { Activity = activity, AthleteTask = dataService.GetAthleteAsync(activity.AthleteID) }).ToList(); // begin enumeration // Wait for them to finish, ie relinquish control of the thread await Task.WhenAll(results.Select(t => t.AthleteTask)); // Set the athletes foreach(var pair in results) { pair.Activity.Athlete = pair.AthleteTask.Result; } 

所以我正在为每个给定的活动下载运动员数据。 但可能是我们要求同一位运动员多次。 我们怎样才能确保GetAthleteAsync方法只会在线获取实际数据(如果它还没有在我们的内存缓存中)?

目前我尝试在GetAthleteAsync方法中使用ConcurrentDictionary Athelete ConcurrentDictionary

 private async Task GetAthleteAsync(int athleteID) { if(cacheAthletes.Contains(athleteID)) return cacheAthletes[atheleID]; ** else fetch from web } 

您可以更改ConcurrentDictionary以缓存Task而不仅仅是Athlete 。 请记住, Task是一个承诺 – 最终会产生T 。 因此,您可以缓存操作而不是结果

 ConcurrentDictionary> cacheAthletes; 

然后,您的逻辑将如下所示:如果操作已经在缓存中,则立即(同步)返回缓存的任务。 如果不是,则启动下载,将下载操作添加到缓存,然后返回新的下载操作。 请注意,所有“下载操作”逻辑都移动到另一个方法:

 private Task GetAthleteAsync(int athleteID) { return cacheAthletes.GetOrAdd(athleteID, id => LoadAthleteAsync(id)); } private async Task LoadAthleteAsync(int athleteID) { // Load from web } 

这样,对同一运动员的多个并行请求将获得相同的Task ,并且每个运动员仅下载一次。

您还需要跳过未完成的任务。 这是我的片段:

 ObjectCache _cache = MemoryCache.Default; static object _lockObject = new object(); public Task GetAsync(string cacheKey, Func> func, TimeSpan? cacheExpiration = null) where T : class { var task = (T)_cache[cacheKey]; if (task != null) return task; lock (_lockObject) { task = (T)_cache[cacheKey]; if (task != null) return task; task = func(); Set(cacheKey, task, cacheExpiration); task.ContinueWith(t => { if (t.Status != TaskStatus.RanToCompletion) _cache.Remove(cacheKey); }); } return task; }i 

在缓存Task-objects提供的值时,您需要确保缓存实现确保:

我有一篇关于使用示例代码缓存任务对象的博客文章 ,该文章确保了上述所有要点,并且可能对您的情况有用。 基本上我的解决方案是将Lazy>对象存储在MemoryCache中。

上述就是C#学习教程:与WhenAll并行执行任务时的任务缓存分享的全部内容,如果对大家有所用处且需要了解更多关于C#学习教程,希望大家多多关注—计算机技术网(www.ctvol.com)!

本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

ctvol管理联系方式QQ:251552304

本文章地址:https://www.ctvol.com/cdevelopment/1007846.html

(0)
上一篇 2021年12月29日
下一篇 2021年12月29日

精彩推荐