我想根据返回值同时运行多个任务。 下面是我想要的粗略代码。
class Program
{
static void tempFunc(string username,string password, ref Queue<KeyValuePair<string, string>> queue)
{
for(int i=0;i<10;i++)
{
Task.Delay(100000);
Console.WriteLine(username + i);
}
queue.Enqueue(new KeyValuePair<string, string>(username, password));
}
static void Main(string[] args)
{
// A queue which is storing the username and password for different sessions and they need
// to be passed to the method being called in Tasks.run
Queue<KeyValuePair<string, string>> queue = new Queue<KeyValuePair<string, string>>();
queue.Enqueue(new KeyValuePair<string, string>("user1", "password1"));
queue.Enqueue(new KeyValuePair<string, string>("user2", "password2"));
queue.Enqueue(new KeyValuePair<string, string>("user3", "password3"));
while(true)
{ // Based on the condition mentioned here(this condition is a method in real which returns a list of
//string, which I will be passing as a parameter to the method being called in Tasks.run but I haven't put that in code here)
if(condition)
{
if(queue.Count != 0)
{
KeyValuePair<string, string> temp = queue.Dequeue();
string username = temp.Key;
string password = temp.Value;
Task.Run(() => tempFunc(username, password, ref queue));
}
}
}
}
}
想法是拥有一个username
和password
池,当任务完成时,它将对使用的username
和password
进行排队,以便可以再次使用。可以有多个任务,它们不相互依赖,即当一个任务正在运行时,另一个任务可以使用其他一组username
和password
和调用方法。这一切都是作为windows service
的一部分运行的. 问题是当我使用提到的代码时,它似乎正在同步工作。即等待一个任务完成,然后运行另一个任务。我做错了什么?或者我用错Tasks.run
方式。
你快到了。很少的更改,您的程序将开始异步工作。
我建议的更改是:
A( 更改功能tempFund
以包含aysnc
。并且无需包含queue
作为此函数的参数。任务完成后,您可以在调用函数中将用户添加回队列。
public static async Task tempFunc(string username, string password)
{
for (int i = 0; i < 10; i++)
{
Console.WriteLine("Before work start : {0}", username + i);
await Task.Delay(2000); //I have reduced it. OP can use his time
Console.WriteLine("After work complete : {0}", username + i);
}
}
B( 将ConcurrentQueue
用于线程安全操作。琼斯也提出了同样的建议。
//Use ConcurrentQueue
var queue = new ConcurrentQueue<KeyValuePair<string, string>>();
C( 将 if 块修改为:
if (queue.Count != 0)
{
var temp = new KeyValuePair<string, string>();
queue.TryDequeue(out temp);
string username = temp.Key;
string password = temp.Value;
Task.Run(async () =>
{
Console.WriteLine("before Task start : {0}", username);
await tempFunc(username, password);
Console.WriteLine("after Task Ends : {0}", username);
queue.Enqueue(new KeyValuePair<string, string>(username, password));
});
记下其他日志,这将使程序异步运行变得明显。