C#异步和等待不工作

C#异步和等待不工作,c#,asynchronous,C#,Asynchronous,为什么以下async和await不工作?我试图了解这一点,我想了解我的代码有什么问题 class Program { static void Main(string[] args) { callCount(); } static void count() { for (int i = 0; i < 5; i++) { System.Threading.Thread.Slee

为什么以下
async
await
不工作?我试图了解这一点,我想了解我的代码有什么问题

class Program
{
    static void Main(string[] args)
    {

        callCount();

    }

    static void count()
    {
        for (int i = 0; i < 5; i++)
        {
            System.Threading.Thread.Sleep(2000);
            Console.WriteLine("count loop: " + i);
        }
    }

    static async void callCount()
    {
        Task task = new Task(count);
        task.Start();
        for (int i = 0; i < 3; i++)
        {
            System.Threading.Thread.Sleep(4000);
            Console.WriteLine("Writing from callCount loop: " + i);
        }
        Console.WriteLine("just before await");
        await task;
        Console.WriteLine("callCount completed");
    }
}
类程序
{
静态void Main(字符串[]参数)
{
callCount();
}
静态无效计数()
{
对于(int i=0;i<5;i++)
{
系统线程线程睡眠(2000);
Console.WriteLine(“计数循环:+i”);
}
}
静态异步void callCount()
{
任务任务=新任务(计数);
task.Start();
对于(int i=0;i<3;i++)
{
系统线程线程睡眠(4000);
WriteLine(“从callCount循环写入:+i”);
}
Console.WriteLine(“就在等待之前”);
等待任务;
Console.WriteLine(“完成呼叫计数”);
}
}

程序开始启动count()方法,但没有完成就退出了。带着等待的任务;语句,我希望它在退出之前等待完成count()方法(0、1、2、3、4)的所有循环。我只得到“计数循环:0”。但它正在经历所有callCount()。这就像等待任务什么都没做一样。我希望count()和callCount()都异步运行,并在完成后返回main。

当执行
async
方法时,它开始同步运行,直到到达
wait
语句,然后其余代码异步执行,执行返回给调用方

在您的代码中,
callCount()
开始同步运行到
wait task
,然后返回到
Main()
方法,由于您没有等待方法完成,因此程序结束时没有方法
count()
可以完成

通过将返回类型更改为
Task
,并在
Main()
方法中调用
Wait()
,可以看到所需的行为

static void Main(string[] args)
{
    callCount().Wait();
}

static void count()
{
    for (int i = 0; i < 5; i++)
    {
        System.Threading.Thread.Sleep(2000);
        Console.WriteLine("count loop: " + i);
    }
}

static async Task callCount()
{
    Task task = new Task(count);
    task.Start();
    for (int i = 0; i < 3; i++)
    {
        System.Threading.Thread.Sleep(1000);
        Console.WriteLine("Writing from callCount loop: " + i);
    }
    Console.WriteLine("just before await");
    await task;
    Console.WriteLine("callCount completed");
}
static void Main(字符串[]args)
{
callCount().Wait();
}
静态无效计数()
{
对于(int i=0;i<5;i++)
{
系统线程线程睡眠(2000);
Console.WriteLine(“计数循环:+i”);
}
}
静态异步任务调用计数()
{
任务任务=新任务(计数);
task.Start();
对于(int i=0;i<3;i++)
{
系统线程线程睡眠(1000);
WriteLine(“从callCount循环写入:+i”);
}
Console.WriteLine(“就在等待之前”);
等待任务;
Console.WriteLine(“完成呼叫计数”);
}
编辑: 以下是代码的执行方式:

(为了更好地理解,允许更改
CallCount()
将类型返回到
Task

  • 程序以
    Main()
    方法开始
  • 调用了
    CallCount()
    方法
  • 任务被创建,所有这些都在同一个线程中
  • 然后任务就开始了。此时,将创建一个并行运行
    Count()
    方法的新线程
  • 在CallCount()中继续执行,因为执行循环并打印“就在等待之前”
  • 然后
    等待任务已到达。这就是异步等待模式发挥作用的时候
    Wait
    Wait()
    不同,它在任务完成之前不会阻止当前线程,而是将执行控制返回到
    Main()
    方法和
    CallCount()
    中的所有剩余指令(在本例中,仅为
    Console.WriteLine(“CallCount completed”);
    )将在任务完成后执行
  • Main()
  • 如果不等待此任务完成,则
    Main()
    中的执行将继续完成程序并销毁任务
  • 如果调用
    Wait()
    (如果
    CallCount()
    无效,则您没有要等待的任务)让任务完成,按住
    Main()
    等待执行
    Count()
    并打印“CallCount completed”
  • 如果要在
    CallCount()
    中等待计数任务完成,而不返回
    Main()
    方法,请调用
    task.wait()
    ,所有程序都将等待
    Count()
    ,但这不是
    wait
    将要做的

    这详细解释了异步等待模式

    希望这个代码的工作流程图对您有所帮助


    如果您不等待
    调用计数的结果,那么您认为会发生什么?在LinqPad中复制您的确切代码,它确实输出了所有
    计数循环:x
    0。。4@MickyD你上了一堂私人课(我知道OP也是这么做的,但那就是错的)@MickyD也许私人课程是个问题-linqpad不需要这个课程declaration@jaykum:除了避免
    async void
    并阻止
    main
    中的主线程以使应用程序不会退出之外,您还不应该使用
    任务
    构造函数或
    任务。启动
    (改为使用
    任务。运行
    )。是,在看到另一个关于堆栈溢出的类似问题和响应后,我尝试了这种方法,但它仍然做同样的事情。我做的和您使用Task作为返回类型时完全一样。我看到我的两个writeline都在执行,但它好像忽略了“wait Task”。它不应该在计数完成之前停止从callCount退出吗?“当您执行一个异步方法时,它开始同步运行,直到到达一个WAIT语句,然后其余代码异步执行,执行返回给调用方”。这似乎不是真的,因为一旦我执行了task.Start(),我就会看到交替的Writeline执行,就好像count()和callCount()循环都在运行一样。当我点击wait任务时,我的程序退出count()。@jaykum我编辑了我的答案,以显示异步等待模式在代码中的工作方式。当我说