【问题标题】:C# task.wait method called not finishedC# task.wait 方法调用未完成
【发布时间】:2018-12-21 06:18:31
【问题描述】:

我试图更好地理解 C# 中的任务和异步操作,并且我正在运行这个示例程序,但我对输出感到困惑。当我运行此程序时,有时程序在

之后不会在 CallMethod 中输出控制台输出
int length = await task

有时确实如此,但当我取消注释时

Console.ReadLine()

它总是运行所有的 CallMethod。

using System;
using System.IO;
using System.Threading;
using System.Threading.Tasks;

namespace Tasks1
{
    class Program
    { 
        static void Main(string[] args)
        {
            Task task = new Task(CallMethod);
            task.Start();
            task.Wait();
            //Console.ReadLine();
        }

    static async void CallMethod()
    {
        string filePath = "/Users/testname/Projects/Tasks1/Tasks1/Sample.txt";
        Task<int> task = ReadFile(filePath);

        Console.WriteLine("Other Work 1");
        Console.WriteLine("Other Work 2");
        Console.WriteLine("Other Work 3");

        int length = await task;
        Console.WriteLine(" Total Length: " + length);

        Console.WriteLine("After work 1");
        Console.WriteLine("After work 2");

    }

    static async Task<int> ReadFile(string file)
    {
        int length = 0;

        Console.WriteLine("File reading is starting");

        using (StreamReader reader = new StreamReader(file))
        {
            string s = await reader.ReadToEndAsync();

            length = s.Length;
        }
        Console.WriteLine("File reading is complete");
        return length;
    }


}
}

【问题讨论】:

    标签: c# asynchronous task


    【解决方案1】:

    async void - 它总是async void :) 基本上,除非你非常清楚为什么要使用它,否则不要使用async void。调用路径无法知道async void 的完成状态,因此从调用者的角度它将运行到第一个非同步await。之后,您将处于线程竞争场景中。它不能参与最外层的Wait()(或await),因为它不报告状态。当所有非后台线程完成时,exe 退出,因此:有时它可能会工作,但大多数情况下不会。添加Console.ReadLine() 会强制它等待更长时间,这就是它起作用的原因。

    基本上:让CallMethod返回Task

    顺便说一句:使用最新的 C# 版本,您也可以将 Main 方法设为 async

        static async Task Main(string[] args) {...}
    

    然后你可以在你的Mainawait。您应该Wait() 处理某项任务的次数几乎为零;通常你应该更喜欢await

    【讨论】:

    • 我认为支持 async void 只是因为按钮单击事件处理程序签名,据我所知,这是它唯一有用的情况。
    • @CRice 当我启动后台工作人员并且 没有人在监听结果 时,我已经使用过几次 - 所有错误处理等都是独立的工人。
    猜你喜欢
    • 2019-10-19
    • 1970-01-01
    • 2023-03-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多