C# 在服务器端做出肯定响应的情况下,有条件的任务取消
我有三个类似的任务C# 在服务器端做出肯定响应的情况下,有条件的任务取消,c#,.net,multithreading,task,task-parallel-library,C#,.net,Multithreading,Task,Task Parallel Library,我有三个类似的任务 public List<CheckResponse> Check(CheckRequest request) { var Responses = new List<CheckResponse>(); List<Task> TaskList = new List<Task>(); Task task1 = new Task(() => { Service gatewayObject
public List<CheckResponse> Check(CheckRequest request)
{
var Responses = new List<CheckResponse>();
List<Task> TaskList = new List<Task>();
Task task1 = new Task(() =>
{
Service gatewayObject = new Service();
var response = gatewayObject.Check();
Responses.Add(response);
});
task1.Start();
TaskList.Add(task1);
Task task2 = new Task(() =>
{
Service gatewayObject = new Service();
var response = gatewayObject.Check();
Responses.Add(response);
});
task2.Start();
TaskList.Add(task2);
Task task3 = new Task(() =>
{
Service gatewayObject = new Service();
var response = gatewayObject.Check();
Responses.Add(response);
});
task3.Start();
TaskList.Add(task3);
Task.WaitAll(TaskList.ToArray());
return Responses;
}
公共列表检查(检查请求)
{
var Responses=新列表();
List TaskList=新列表();
任务task1=新任务(()=>
{
服务网关对象=新服务();
var response=gatewayObject.Check();
答复。添加(答复);
});
task1.Start();
任务列表。添加(任务1);
任务task2=新任务(()=>
{
服务网关对象=新服务();
var response=gatewayObject.Check();
答复。添加(答复);
});
task2.Start();
任务列表。添加(任务2);
任务task3=新任务(()=>
{
服务网关对象=新服务();
var response=gatewayObject.Check();
答复。添加(答复);
});
task3.Start();
任务列表。添加(任务3);
Task.WaitAll(TaskList.ToArray());
回应;
}
他们每个人都请求服务,并能返回积极的结果
所以我想取消另外两个任务,如果其中任何一个返回正结果
我无法访问服务端代码,因此无法对服务端进行任何更改。您可以使用
Task.WaitAny(TaskList.ToArray())
,然后取消其他任务,但结果必须是肯定的!所以WaitAny不是我们的选择。您应该创建取消令牌并将其传递给所有三个任务,只有在结果为正时才将其抛出!旁注:您这里有一个(很可能)潜在的线程错误-您的三个任务中的代码都在修改响应
,这通常不是并发访问的安全类。Darko Maric Programer是的,您是对的,但如果在我这边运行代码,取消令牌可以取消任务,因此如果gatewayObject.Check()运行代码,我无法停止它尚未完成。如果您的gatewayObject.Check
不支持取消(通过接受CancellationToken
)-您无法真正“取消”任何内容(也不需要)。您只需等待任务的第一个肯定响应。WaitAny
(在循环中,如果任务失败,那么您可以对其余任务再执行一个task.WaitAny
),并忘记其他任务(不要将响应添加到列表中-您只需要一个响应,就可以从任务中返回它)。您可以使用task.WaitAny(TaskList.ToArray())
然后取消其他任务,但结果必须为正数!因此WaitAny不是选项。您应该创建取消令牌,并将其传递给所有三个任务,仅当结果为正数时才将其抛出!旁注:您有一个(极有可能)这里有潜在的线程错误-您的三个任务中的代码都在修改响应
,这通常不是并发访问的安全类。Darko Maric Programer是的,您是对的,但如果运行代码在我这边起作用,取消令牌可以取消任务,因此如果gatewayObject.Check()尚未完成。如果您的gatewayObject.Check
不支持取消(通过接受CancellationToken
)-您无法真正“取消”任何内容(也不需要)。您只需等待任务的第一个肯定响应。WaitAny
(在一个循环中,如果任务失败,您可以对其余的任务再执行一个任务。WaitAny
),并忘记其他任务(不要将响应添加到列表中-您只需要一个响应,因此从任务返回它)。