问题标签 [taskcompletionsource]

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 回答
330 浏览

c# - C# 任务完成源

我对问题陈述有一个要求,就像说,当一个事件被触发时,我必须调用一个任务完成源,使用异步和等待。将发生多个事件,并且每次发生事件时都必须调用此任务完成。(还会发生多个任务,并提高此任务的完成度)

比如说,有几何形状和与这些形状相对应的空白空间。当这些对象形状被放置在这个空间中时,应该触发一个事件,这会引发任务完成源。

所以想要实现一个使用任务完成源的程序,根据发生的事件、依赖注入、系统事件/通知以及检查事件是否完成。(对于多个事件)。

希望我对要求很清楚,但由于问题陈述有点棘手,因为它涉及很多 TPL Async 概念,我尽力解释,因此对上面的形状游戏进行了类比。

任何有用的建议/链接/建议都会很棒。

提前致谢!!!..

0 投票
2 回答
42 浏览

c# - 需要使用 TaskCompletionSource 保持代码执行直到属性为空

我有一堂课

我在 C# 代码中使用这个类

但我想保持我的代码执行直到message属性为空。

我有一种不同的方法,在一段时间后填充属性,这取决于用户,它可以在 2 秒或 2 分钟内填充。但是,一旦用户填写了消息,我就需要在它所在的位置执行。

我可以在其中使用 while 但我只想使用TaskCompletionSource.

0 投票
1 回答
379 浏览

c# - 如何对依赖于 TaskCompletionSource 的类进行单元测试?

我有一门课取决于TaskCompletionSource

该类的一个示例如下所示:

我使用xUnit.net作为我的测试框架。

(见代码中的注释)

0 投票
0 回答
147 浏览

c# - 在发布模式下编译代码时,异步方法中的 TaskCompletionSource 对象变为 null

我正在使用 .Net 4.6.1 版和 VS2015 Update 3。

我面临一个奇怪的问题,因为一段代码在调试模式下编译时工作正常,但是,在发布模式下编译时它会因 NullReferenceException 而失败。

我有一个异步方法,它使用 TaskCompletionSource 来等待任务完成,如果没有收到响应,我会在 5 秒后再次重试。我在下面给出的简化示例代码中重现了这个错误。

在上面的代码示例中,如果变量 ' tcs ' 变为空,我会显示一条消息。在发布模式下编译代码时收到错误消息;尽管如此,它在调试模式下工作正常。

此外,为了解决这个问题,我只是将下面的代码行移到了 try 块之外,一切正常。

对我来说,这似乎是某种 .Net 错误。

谁能帮我理解这种尴尬的行为?

编辑1:

好吧,这个问题有点难以置信,因此,我创建了一个重现此问题的工作示例项目。请从以下链接下载并在调试和发布模式下编译代码。

下载样本

下载可执行文件

编译完成后,请以两种模式一一运行可执行文件。

在调试模式下,测试应该在 15 秒后完成,但是,它会显示一条消息,即“tcs”变量在发布模式下为空,并且在按下 Ok 按钮时会抛出 NullReferenceException。

0 投票
2 回答
2545 浏览

c# - 在 C# 中使用 Polly,我可以等到时间跨度过去或任务终止后再重试吗?

我正在尝试在 C#中使用Polly包。我想运行一些代码,然后,如果失败,请等待并重试。目前我的循环看起来与此类似:

即:等待 10 秒或直到这些任务完成源之一收到信号并终止。然后重试。

我想做的是这样的(Polly API 不支持):

有可能用波莉做这样的事情吗?我可以等待 TimeSpan 以外的任何东西吗?

关于我在上面的例子中等待的两个任务:一个任务是取消,表明整个事情应该关闭。另一个是“唤醒连接尝试”任务,其终止指示“此对象的状态已更改;尝试再次调用它”。在这两种情况下,我都希望我的循环立即继续下一次迭代,而不是等待超时过去。

目前等待超时并不是那么糟糕,因为它只有 10 秒,但如果我将其更改为指数退避,那么突然超时可能会很长。因此,我希望中断超时并直接进行下一次迭代。

注意:我的重试循环不一定要遵循异步等待模式。如果等待部分是同步和阻塞的就可以了。我只想能够使用任务完成源取消等待。

0 投票
1 回答
194 浏览

c# - 如何在另一个线程中继续 TaskCompletionSource<>?

TaskCompletionSource<>经常使用。我有一个网络协议设计,我在一个 tcp/ip 连接中接收到许多流。我对这些流进行解复用,然后将新内容通知相应的“子连接”。

那些“子连接”(通过 等待await)然后应该在新线程中继续。

通常我通过将TaskComplectionSource<>.Set调用放在匿名ThreadPool.QueueUserWorkItem方法中来解决此类问题,如下所示:

如果我不这样做,相应的await tcs.Task调用将在调用的线程中继续tcs.SetResult

但是,我知道这不是做事的正确方法。也可以自己编写一个SynchronizationContext(或其他东西)来指示await调用在另一个线程中继续。

我的主要问题是:我将如何以“最佳实践”的方式做到这一点?

我希望在这里也能避免ThreadPool开销,因为与阻塞线程并等待ManualResetEvent- 即使SynchronizationContext(或其他)也可能使用ThreadPool.

请不要告诉我在一个 tcp/ip 连接中多路复用某些东西通常是一个坏主意,或者我应该只使用 System.IO.Pipelines、REST 或其他什么。这是我的场景。谢谢你。

0 投票
2 回答
795 浏览

c# - 在 await Task.Run 调用中使用 TaskCompletionSource

我遇到了一些意想不到的行为,我想对此有所了解。我创建了一个简单的例子来演示这个问题。我使用 调用异步函数Task.Run,它将不断生成结果,并用于IProgress向 UI 传递更新。但是我想等到 UI 实际更新后再继续,所以我尝试按照其他一些帖子中的建议使用 TaskCompletionSource(这似乎有点相似:Is it possible to await an event instead of another async method?.)我期待最初Task.Run的等待,但正在发生的是内部发生的等待似乎将其向前移动,并且“END”发生在第一次迭代之后。Start()是入口点:

有了这个,我得到:

而不是我想要得到的是:

我假设我对 Tasks 和 await 以及它们的工作方式有误解。我确实想StartDataPush成为一个单独的线程,我的理解是它是。我的最终用途有点复杂,因为它涉及繁重的计算、更新到 WPF UI 以及发回通知它已完成的事件,但机制是相同的。我怎样才能实现我想要做的事情?

0 投票
1 回答
107 浏览

c# - 我想知道使用 TaskCompletitionSource 是否是一个糟糕的选择

我必须在这里补充一下,我不是 Stackoverflow 上的资深提问者,所以我很高兴收到有关我的问题可能不适合这里的反馈。

包装非异步调用时等待 TaskCompletitionSource 是一件坏事吗?

这是我的用例:

我有一个处理程序类,它Func<T, Task>在事件发生时调用函数回调。处理程序从我的应用程序外部调用并通知我的 UI。有两种方法 A 和 B 用作回调。A 调用异步 HTTP 客户端,B 进行计算。在这两种情况下,await 调用都会解冻 UI,然后更新属性。

A:

乙:

我的问题是,使用 TaskCompletionSource 包装非异步调用是一种不好的做法吗?

文档说明了以下内容。

如果要为现有异步操作或事件创建任务包装器,请使用 TaskCompletionSource。https://docs.microsoft.com/en-us/archive/msdn-magazine/2013/march/async-await-best-practices-in-asynchronous-programming

另一种可能性是调用Task.Run(),但对我来说感觉更糟。不使用 Async 会导致 UI 冻结,这并不是我真正想要的,尽管它可能是最干净的解决方案。

--------> 更新

正如其他人所说,Task.Run() 在这里非常好。

我应该注意到我的 B: 看起来不同 B:

使用下面的 Task.Run() 找到更好的选择。

我还应该注意,当方法离开时,字节(示例中未显示)被释放。

0 投票
0 回答
61 浏览

c# - C# - 如何正确等待另一个类异步提供数据?

我有一群“工人”,在某些时候需要来自我的 HTTP 服务器的唯一密钥才能继续执行。这些密钥有时会在工作人员需要它们之前到达,在这种情况下,我只想为工作人员提供密钥,以便它可以继续执行。但是,如果没有剩下的键,我希望任务中的代码执行停止,直到提供键。我还希望首先使用首先提供的密钥。

我试图实现一个单例,其中可以从 HTTP 服务器提供密钥并由工作人员从中检索,但现在执行似乎陷入僵局。

我的代码:

密钥处理程序.cs

工人.cs

HTTPServer.cs

0 投票
2 回答
258 浏览

c# - 使用 TaskCompletionSource 构建 IAsyncEnumerable

我有一个接受 anIEnumerable并返回使用 yield 运算符转换的方法。要转换可枚举的一个元素,我首先需要知道另一个元素的值。因此,我想到了使用 aTaskCompletionSource来创建类似“promise”的东西。

这里的问题是,如果“a”以外的任何值是 first 的值,则此代码会导致死锁TestFieldA。一种解决方案是在将枚举传递给方法之前对其进行排序——在这种情况下,完全不需要TaskCompletionSource。但是,我想知道是否可以在没有这个的情况下完成。我也知道这可以通过一些 LINQ 查询来完成,但这需要多次枚举输入,我想避免这种情况。

这就是我想要达到的目标。(仅适用于第一个TestFieldA == "a"