Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/list/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 异步等待错误的执行顺序_C#_Asynchronous_Async Await - Fatal编程技术网

C# 异步等待错误的执行顺序

C# 异步等待错误的执行顺序,c#,asynchronous,async-await,C#,Asynchronous,Async Await,我试图掌握异步等待模式。下面的示例中,我实现了 这个小程序: private async void asynchWork() { // Line 1 Task<string> readTask = asynchAwaitWork(); // Line 2 synchWork(); // Line 3 string result = await readTask; // Line 4 Debug.WriteLine(

我试图掌握异步等待模式。下面的示例中,我实现了 这个小程序:

private async void asynchWork()
{
    // Line 1
    Task<string> readTask = asynchAwaitWork();

    // Line 2
    synchWork();

    // Line 3
    string result = await readTask;

    // Line 4
    Debug.WriteLine(result);
    Debug.WriteLine("The End");
}
private void synchWork()
{
    for (int i = 0; i < 5; i++)
    {
        Debug.WriteLine("SynchWork For i : " + i);
        Thread.Sleep(750);
    }
}

private async Task<string> asynchAwaitWork()
{
    for (int i = 0; i < 15; i++)
    {
        Debug.WriteLine("A-SynchWork For i : " + (i+111));
        Thread.Sleep(750);
    }

    return "finished";
}
多谢各位。我学到了很多:)

只要替换
Thread.Sleep(750)等待任务。延迟(750)异步工作
事情是asynchAwaitWork开始在主线程中工作。异步工作-这是用于继续的。使用wait关键字,您可以创建continuation,这就是它开始并行工作的原因。
还要将当前线程Id添加到输出中,以查看发生了什么。例如:

private async void asynchWork()
{
    // Line 1
    Task<string> readTask = asynchAwaitWork();

    // Line 2
    synchWork();

    // Line 3
    string result = await readTask;

    // Line 4
    Debug.WriteLine(result);
    Debug.WriteLine("The End");
}
private void synchWork()
{
    for (int i = 0; i < 5; i++)
    {
        Debug.WriteLine("SynchWork For i : " + i + " and thareadId = " + Thread.CurrentThread.ManagedThreadId);
        Thread.Sleep(750);
    }
}

private async Task<string> asynchAwaitWork()
{
    for (int i = 0; i < 15; i++)
    {
        Debug.WriteLine("A-SynchWork For i : " + (i + 111) + " and thareadId = " + Thread.CurrentThread.ManagedThreadId);
        await Task.Delay(750);
        //Thread.Sleep(750);
    }

    return "finished";
}
您将看到所有这些都发生在同一个线程中。
因此,请注意这一点,您可以使用
wait Task.Delay(750).configurewait(false)以避免这种情况。

仅查看主程序:

当第3行已经执行时,可以保证在第1行中得到的任务已经完成了其中的任何内容

在第2行,您不能保证任务已经开始执行或已经完成。你不知道它是否会并行运行。您所知道的是,有一个任务可以计划执行

在函数
asynchwaitwork
中创建的任务的实现是完全同步的。该实现细节使得它在返回最终(在本例中是立即)返回字符串的任务时完全完成了打印工作


请注意,您创建的任务不会打印任何内容。在当前实现中打印“A-SynchWork For i”消息是创建任务的一个副作用。

您应该得到
asynchAwaitWork
的编译器警告,它给出了为什么没有得到的线索work@ScottChamberlain等待是失踪的,它说。因此,它将同步执行。“我只是不太明白为什么从这些小信息中,”MongZhu接着对这个警告做了一些研究。上面有很多信息。@Servy好提示,我现在正在做。使用wait创建了一个可以并行运行的任务,如果我不使用它,那么编译器将通过主线程跟踪它!我说得对吗?不太对。使用
wait
不会创建可以并行运行的任务<代码>等待
异步等待任务完成。wait和async不会使任何东西异步。它们允许您更轻松地使用已经异步的方法。同样:wait或async不会创建新的异步。您必须已经有一个异步操作等待。如果这是在控制台应用程序中运行,它们将并行运行,但是,如果在设置了
SyncronisationContext.Current
的情况下运行此操作,它将运行第一个
asynchwaitwork
,然后运行所有
synchWork
,然后运行其余的
asynchwaitwork
。您需要执行
等待任务。延迟(750)。配置等待(false)
或do
Task readTask=Task.Run(()=>asynchAwaitWork())是,任务。延迟(750)将在当前上下文中继续。所以,若我们在WPF应用程序(例如)的UI线程中运行它,那个么continuation将在UI线程中运行。谢谢,@ScottChamberlain,你说得对。@tym32167“使用wait关键字,你在创建continuation”为什么?“你能详细说明一下吗?”MongZhu不确定我能否完整地描述它的工作原理。但您必须知道,wait和async不是处理器或IL指令,编译器将这些关键字转换为某些构造。要深入了解这一点,您可以尝试此链接,谢谢。在过去的一个小时里我已经掌握了很多。阅读你的链接现在伟大的解释!那么这是否意味着在
asynchwaitwork
中:
asynchtask
部分会创建一个任务,但它永远不会并行运行,因为没有一行代码表示
Start(…)
run(…)
。这就是为什么它也从不打印任何东西!当
asynchwaitwork
到达return语句时,它将返回值分配给传递给第3行中的
result
的任务。你回答的最后一部分真的很有启发性!对于聊天格式,更多的讨论可能更好。但是您的
asynchwaitwork
相当于
console.WriteLine(“这是一个副作用”);返回Task.FromResult(“已完成”)
。等待该任务与它前面的WriteLine无关。
private async void asynchWork()
{
    // Line 1
    Task<string> readTask = asynchAwaitWork();

    // Line 2
    synchWork();

    // Line 3
    string result = await readTask;

    // Line 4
    Debug.WriteLine(result);
    Debug.WriteLine("The End");
}
private void synchWork()
{
    for (int i = 0; i < 5; i++)
    {
        Debug.WriteLine("SynchWork For i : " + i + " and thareadId = " + Thread.CurrentThread.ManagedThreadId);
        Thread.Sleep(750);
    }
}

private async Task<string> asynchAwaitWork()
{
    for (int i = 0; i < 15; i++)
    {
        Debug.WriteLine("A-SynchWork For i : " + (i + 111) + " and thareadId = " + Thread.CurrentThread.ManagedThreadId);
        await Task.Delay(750);
        //Thread.Sleep(750);
    }

    return "finished";
}
[STAThread]
void Main()
{
    var window = new Window();
    window.Loaded += (s, e) => {
        asynchWork();
    };
    window.ShowDialog();
}