Sleep() 方法后的代码片段没有被执行
Posted
技术标签:
【中文标题】Sleep() 方法后的代码片段没有被执行【英文标题】:Code snippets after Sleep() method does not get executed 【发布时间】:2021-09-01 19:51:03 【问题描述】:我正在尝试理解 C# 中的任务和并行性。我在控制台应用程序中有以下代码。我期待 Sleep() 方法之后的代码在 3 毫秒后运行,但程序退出了。
任何人都可以提供见解,说明为什么它没有等待 3 毫秒并完成剩余代码的执行。如何让剩余代码在 3 毫秒后执行?
static void Main(string[] args) Task task = new Task(() => Console.WriteLine("Task on thread 0 started.", Thread.CurrentThread.ManagedThreadId); Thread.Sleep(3000); Console.WriteLine("Task on thread 0 finished.", Thread.CurrentThread.ManagedThreadId); ); task.Start(); Console.WriteLine("this is the main thread");
【问题讨论】:
问:我期待 Sleep() 方法之后的代码在 3 毫秒后运行,但程序退出了。 A:程序退出是因为你没有做任何事情来阻止它退出。就个人而言,我建议在您的最终“Console.WriteLine()”之后放置一个Console.ReadLine()。还有其他选择。例如,您可以在 Main() 中调用 task.Wait():docs.microsoft.com/en-us/dotnet/api/…Sleep
的参数以毫秒为单位。 Sleep(3000)
将休眠 3 秒,而不是 3 毫秒。您正在将后台工作分派到线程池线程(这是一个“后台线程”,不会让您的应用程序保持活动状态)。程序的工作方式是启动应用程序,将工作分派到线程池线程。它开始,然后停止 3 秒。同时,前台线程继续运行并退出,在 Sleep 结束之前结束您的应用程序的执行。
附带说明,专家不赞成使用Task
构造函数创建任务,除非您正在执行需要它的高级操作。启动delegate-based 任务的常用方法是使用Task.Run
方法。
感谢 @paulsm4 提供对代码的见解。我知道为什么代码没有按预期工作。
@Flydog57 感谢您提供见解。这很有帮助。
【参考方案1】:
使用await Task.Delay(3000);
代替Thread.Sleep(3000);
(示例如下)。
请注意,下面的 sn-p 是原始代码 sn-p 的修改版本,但对演示进行了修改。
static async Task Main()
await Task.Run(async () =>
Console.WriteLine("Task on thread 0 started.", Thread.CurrentThread.ManagedThreadId);
await Task.Delay(3000);
Console.WriteLine("Task on thread 0 finished.", Thread.CurrentThread.ManagedThreadId);
);
Console.WriteLine("this is the main thread");
注意:以上 sn-p 仅用于探索Tasks
,因此不能在生产环境中使用。简单地在问题代码 sn-p 中删除 Task
的使用在功能上是等效的,但是此解决方案旨在说明如何使用 Task
。
【讨论】:
await 运算符只能与异步 lambda 表达式一起使用。没有异步就不会编译这段代码。 等待Task.Run
有什么意义?您可以删除该代码,它会运行相同的。
@Enigmativity 问题的第一句话解释说:我正在尝试理解 C# 中的任务和并行性。.
@Enigmativity - 为您的问题提供理由“等待Task.Run
有什么意义?”。学习、理解和探索Tasks
。
@Enigmativity - 很公平,感谢您的建议。答案更新,免责声明意图纯粹是教育性的。【参考方案2】:
您需要等待任务完成。而 3000 相当于 3 秒……不是 3 毫秒。
Task task = new Task(() =>
System.Console.WriteLine("Task on thread 0 started.",
Thread.CurrentThread.ManagedThreadId);
Thread.Sleep(3000);
System.Console.WriteLine("Task on thread 0 finished.",
Thread.CurrentThread.ManagedThreadId);
);
task.Start();
System.Console.WriteLine("this is the main thread");
task.Wait();
【讨论】:
是的,你是对的,它是 3 秒,但它没有打印,正如你在输出窗口中看到的那样谢谢!! @sabin 代码已编辑。您需要根据您的要求调整 task.wait()。 我找不到@StephenCleary 关于手工艺Task
s 的文章。但不建议手动调用 Task ctor。首选方式是Task.Run
或Task.Factory.StartNew
。以上是关于Sleep() 方法后的代码片段没有被执行的主要内容,如果未能解决你的问题,请参考以下文章