问题标签 [cancellationtokensource]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
1 回答
248 浏览

c# - 如何解决此 Task/CancellationToken 问题?

我正在运行这段代码;

我得到这个输出

如何解决问题Count value 8

它应该说成功并停在那里。

0 投票
1 回答
845 浏览

c# - 在任务中调用 CancellationTokenSource.Cancel() 不会将 Task.IsCanceled 设置为 true

如果我cancellationTokenSource.Cancel在与取消令牌关联的任务中调用,OperationCancelledException则会正确抛出 ,但是task.IsCanceled并不总是true像预期的那样更新并设置为 。

可以使用以下 nUnit 测试快速演示该问题:

当我运行这个测试时,测试通过了,但是,当我调试这个测试(使用 Resharper 测试运行器)时,测试失败了。

我认为这与 Resharper 没有任何关系,我认为 Resharper 可能只是在创造一些可能暴露 .Net 中的问题的条件。或者,也许我只是在做一些完全错误的事情......有什么见解吗?

0 投票
1 回答
67 浏览

c# - 在进行长时间运行之前立即取消操作?

我以下列方式使用 AsParallel 与 WithDegreeOfParallelism 和 WithCancellation

这是我对此的理解。一次只处理两个传入序列。一旦其中一个请求完成,就会处理更多项目。但是,如果发起取消请求,则将根本处理来自传入队列的尚未提取的那些项目。基于这种理解,我创建了以下代码。

这是我运行它时的输出。

ThreadID = 3 -> 员工 1 -> 睡眠 1058
ThreadID = 1 -> 员工 7 -> 睡眠 1187
ThreadID = 1 -> 员工 8 -> 睡眠 1296
ThreadID = 1 -> 员工 9 -> 睡眠 1614
ThreadID = 1 -> 员工 10 -> 为 1607 睡眠
ThreadID = 1 -> 员工 5 -> 为 1928 睡眠
ThreadID = 3 -> 员工 2 -> 为 1487 睡眠
ThreadID = 3 -> 员工 3 -> 为 1535 睡眠
ThreadID = 3 - > 员工 4 -> 为 1265 休眠
ThreadID = 3 -> 员工 5 -> 为 1248 休眠
ThreadID = 3 -> 员工 6 -> 为 807 休眠
现在正在等待
ThreadID = 3 -> 员工 6 完成
ThreadID = 4 ->员工 1 完成
ThreadID = 5 -> 员工 7 完成
ThreadID = 6 -> 员工 8 完成
ThreadID = 3 -> 员工 5 完成
ThreadID = 4 -> 员工 9 完成
ThreadID = 5 -> 员工 10 完成
ThreadID = 6 -> 员工 5 完成
ThreadID = 3 -> 员工 4 完成
ThreadID = 7 -> 员工 2 完成
ThreadID = 8 -> 员工 3 完成
全部完成

这是我的问题(根据我对事物的理解)。

  1. 我期待对于某些员工 ProcessThisEmployee 根本不会被调用,因为它将被取消,但它会被所有员工调用
  2. 即使调用 ProcessThisEmployee 方法,它也会通过以下代码路径,这也不会发生

    /li>

于是我改了ProcessThisEmployee,基本上是在Sleep之后移动了token.IsCancellationRequested消息如下。

现在我得到以下输出。

我的问题是我对这个工作流程有什么误解。我基本上想尽快取消操作而无需长时间运行(睡眠只是这种情况下的一个例子,但它可能非常昂贵)

0 投票
1 回答
1316 浏览

c# - 任务循环退出的 CancellationTokenSource 和退出标志之间的区别

我想知道使用 CancellationTokenSource 结束循环任务和退出标志之间是否有任何区别

取消令牌来源:

退出标志:

对我来说,使用 CancellationTokenSource 没有任何意义,顺便说一句,有什么理由可以将取消令牌作为参数添加到任务工厂?

非常感谢您的任何回答。

最好的 ragards teamol

0 投票
3 回答
26120 浏览

c# - 取消 HttpClient 请求 - 为什么 TaskCanceledException.CancellationToken.IsCancellationRequested 为假?

给定以下代码:

我希望ex.CancellationToken.IsCancellationRequestedtruecatch 块内,但事实并非如此。我是不是误会了什么?

0 投票
1 回答
2404 浏览

c# - default(CancellationToken) 怎么会有对应的 CancellationTokenSource

当我创建一个默认值时CancellationToken,我可以在调试器中看到它CancellationToken有一个CancellationTokenSource与之关联的存储在私有m_source字段中:

不为空

我想知道对于结构来说,default关键字“将根据它们是值类型还是引用类型,将结构的每个成员初始化为零或null”并且CancellationTokenSource是引用类型。

CancellationToken确实有 2 个设置此字段的构造函数,但是它们不相关,因为default(CancellationToken)不调用构造函数并且new CancellationToken()(具有完全相同的行为)不调用构造函数,因为结构不能具有无参数构造函数(尚未)。

0 投票
4 回答
18322 浏览

c# - 链接取消令牌

我使用传递的取消令牌,以便可以干净地关闭我的服务。该服务具有不断尝试连接到其他服务的逻辑,因此令牌是打破在单独线程中运行的这些重试循环的好方法。我的问题是我需要调用具有内部重试逻辑的服务,但如果重试失败,则在设定的时间段后返回。我想创建一个带有超时的新取消令牌,这将为我做这件事。这样做的问题是我的新令牌没有链接到“主”令牌,所以当主令牌被取消时,我的新令牌仍然有效,直到它超时或建立连接并返回。我想做的是将两个令牌链接在一起,这样当主令牌被取消时,我的新令牌也将取消。我尝试使用CancellationTokenSource.CreateLinkedTokenSource方法但是当我的新令牌超时时,它也取消了主令牌。有没有办法用令牌做我需要做的事情,或者是否需要更改重试逻辑(可能无法轻松做到这一点)

这是我想做的事情:

Master Token - 传递各种功能,以便服务可以干净地关闭。临时令牌 - 传递给单个函数并在一分钟后设置为超时

如果主令牌被取消,临时令牌也必须被取消。

当临时令牌到期时,不得取消主令牌。

0 投票
3 回答
1344 浏览

c# - 任务取消抛出异常

因此,根据对这篇文章的回答:

2) 如果任务主体也在监视取消令牌并抛出包含该令牌的 OperationCanceledException(这是 ThrowIfCancellationRequested 所做的),那么当任务看到该 OCE 时,它会检查 OCE 的令牌是否与任务的令牌匹配。如果是这样,则该异常被视为对合作取消的确认,并且任务转换到 Canceled 状态(而不是 Faulted 状态)。

由此我了解到,通过将令牌传递给任务的构造函数,然后调用相同的令牌的 ThrowIfCancellationRequested() 方法,任务实际上会和平终止,而无需我显式地捕获 OperationCanceledException。

然而事实证明,抛出了一个异常,所以我相信我可能误解了机制。

我的代码:

0 投票
1 回答
3525 浏览

c# - 在任务取消时处理 CancellationTokenSource 的代码是否正确?

我在我面前看到这段代码,我很怀疑:

取消后直接调用 _cts.Dispose() 是否安全?如果它想这样做,那是否会处理被取消的任务以成功等待 CancellationToken 所需的 CancellationTokenSource 的底层资源?

0 投票
1 回答
942 浏览

c# - 在任务执行委托中延迟取消支持的正确方法是什么?

我在 MSDN 或这里都没有看到任何关于如何实现这一点的具体提及。用例有点模糊,但我怀疑仍然有效。

上面的代码将尝试在 100 毫秒后取消task包含分离的子延迟任务的任务,并等待task完成,这将生成一个AggregateException(由于取消)。这样做的问题是它task变得有问题而不是被取消。这是预期的行为,因为延迟任务未附加到 parent task,即使两者共享相同的取消令牌。

我的问题特别与您将如何将 a 附加Task.Delay到已经运行的任务有关。如果您有权访问父任务,甚至可以这样做吗?如果不可能,或者不能访问父任务实例,那么处理这种情况的正确方法是什么?

我能想到的最好的解决方法是将延迟任务包装Wait在 try/finally 块中,并明确地尝试使任务取消冒泡。

虽然有效,但感觉不太对劲,但我不确定是否有更好的方法来实现这一点。期望的结果是父任务去Canceled而不是Faulted如果取消发生。因此,如果取消的起源发生在分离的子任务中,则父任务仍应转换为Canceled.

注意:我故意在这里省略了 async/await,只是因为它似乎并没有改变问题或结果。如果不是这种情况,请提供一个例子。