如何构造下面的代码以便调用异步方法?
Parallel.For(0, elevations.Count(), delegate(int i)
{
allSheets.AddRange(await BuildSheetsAsync(userID, elevations[i], includeLabels));
});
答案 0 :(得分:31)
Parallel.For()
与async
方法不兼容。如果您不需要限制并行度(即,您可以同时执行所有任务),则只需启动所有Task
,然后等待它们完成:
var tasks = Enumerable.Range(0, elevations.Count())
.Select(i => BuildSheetsAsync(userID, elevations[i], includeLabels));
List<Bitmap> allSheets = (await Task.WhenAll(tasks)).SelectMany(x => x).ToList();
答案 1 :(得分:4)
我建议你看一下我几天前提出的这个问题并最终回答自己,基本上我正在寻找一个并行和异步ForEach方法。
该方法使用SemaphoreSlim
并行处理事物,并接受异步方法作为输入操作。
您可能还想查看我在答案结尾处提供的两个链接,它们对实现此类行为非常有用,并且它们还包含使用Partitioner
执行此操作的另一种方法代替。
就个人而言,我不喜欢Parallel.For
,因为它是同步通话,正如我给出的链接所解释的那样;我希望它全部'异步': - )
答案 2 :(得分:0)
您可以尝试使用我正在使用的这段代码。它使用foreach和SemaphoreSlim来实现并行异步。
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from nsepy import get_history
import datetime as dt
%matplotlib inline
start = dt.datetime(2015, 1, 1)
end = dt.datetime.today()
infy = get_history(symbol='INFY', start = start, end = end)
infy.index = pd.to_datetime(infy.index)
hdfc = get_history(symbol='HDFC', start = start, end = end)
hdfc.index = pd.to_datetime(hdfc.index)
reliance = get_history(symbol='RELIANCE', start = start, end = end)
reliance.index = pd.to_datetime(reliance.index)
wipro = get_history(symbol='WIPRO', start = start, end = end)
wipro.index = pd.to_datetime(wipro.index)
open_prices = pd.concat([infy['Open'], hdfc['Open'],reliance['Open'],
wipro['Open']], axis = 1)
open_prices.columns = ['Infy', 'Hdfc', 'Reliance', 'Wipro']
f, (ax1, ax2) = plt.subplots(1, 2, sharey=True)
axes[0, 0].plot(open_prices.index.year,open_prices.INFY)
axes[0, 1].plot(open_prices.index.year,open_prices.HDB)
axes[1, 0].plot(open_prices.index.year,open_prices.TTM)
axes[1, 1].plot(open_prices.index.year,open_prices.WIT)
用法:
brew install chargepoint/xcparse/xcparse
任何建议请让我知道。
答案 3 :(得分:-2)
在Parallel.For
中调用异步方法的最简单方法是:
Parallel.For(0, elevations.Count(), async i =>
{
allSheets.AddRange(await BuildSheetsAsync(userID, elevations[i], includeLabels));
});
==============
MarioDS在评论中提到绝对正确,在这种情况下,您可能有未观察到的异常。这绝对是非常重要的事情,你应该始终牢记然后与异步代表达成协议。
在这种情况下,如果您认为自己有例外,可以在委托中使用try/catch
阻止。或者在某些情况下,如果您的情况有利,您可以订阅TaskScheduler.UnobservedTaskException事件。