2017-05-20 53 views
-1

我仍然在努力完全理解异步/等待的方法。任何人都可以告诉我,因为在主题确实等待Task.Run后面呢?有时候人们在做异步方法,包括等待,但是有时候人们会做不使用异步方法的Task.Run。什么是正确的方法?确实等待Task.Run()

+5

不,不。你可能会发现斯蒂芬克利里的[没有线程](https://blog.stephencleary.com/2013/11/there-is-no-thread.html)很有帮助。 –

回答

0

async运营商只是在一种方法中打开使用运营商awaitawait运营商将处理任何等待。在.NET中,TaskTask<T>等待 s的一些示例。

Task.Run回报TaskTask.Run<T>回报Task<T>和我说,他们都awaitable所以你可以await他们。

,如果你愿意,你甚至可以编写自己的awaitable类型:你只需要确保满足什么被认为是一个awaitable的要求。 等待需要提供GetAwaiter的实现,就是这样。下面是一个awaitableexample

public struct SimpleInt32Awaitable 
{ 
    public SimpleInt32Awaiter GetAwaiter() 
    { 
     return new SimpleInt32Awaiter(); 
    } 
} 

public struct SimpleInt32Awaiter 
{ 
    public bool IsCompleted { get { return true; } } 

    public void OnCompleted(Action continuation) 
    { 
    } 

    public int GetResult() 
    { 
     return 5; 
    } 
} 

现在你可以这样做:

// Within some other class 
static async void SimpleWaitAsync() 
{ 
    SimpleInt32Awaitable awaitable = new SimpleInt32Awaitable(); 
    int result = await awaitable; 
} 
-1

有你在哪里使用异步限制和等待的情况下 - 这是,一般情况下,为什么你会有时会看到使用Task.Run - 这允许您在同步方法中使用异步代码。

有必要的一个示例是,在MVC中使用Child Actions时 - 框架不支持异步子操作,因此必须使用Task.Run调用异步代码。

0

确实在等待Task.Run的背后?

其他人已经链接到C#并发,There Is No Thread克利里的很多优秀的博客文章之一。

不,它不会在幕后使用Task.Run

await对于不止Task.Run是有用的。它用于在之后运行代码已完成。这可能是由Task.Run创建的计算任务,但它也可以是数据检索,例如ReadLineAsyncTask是用来模拟所有这些东西的类。

Task.Runused排队工作线程池上运行。在编写CPU绑定代码时这是适当的,但是you shouldn't use Task.Run when dealing with IO-bound operations。在这种情况下,您的异步代码(可能使用async/await)应该使用异步IO方法,如WriteLineAsync和前述的ReadLineAsync

这是使用Task.Run在工作线程上运行阻止代码的反模式。你永远不想这样做,即使它确实要解锁你的GUI线程。

有时人们在做异步metod包括await,但有时人们会做不使用异步方法的Task.Run。什么是正确的方法?

可以使用Task.Run确实创造一个Task就让它运行,而无需使用awaitContinueWith。这些被称为“火灾和遗忘”任务。他们很少是一个好主意。与使用await时不同,该任务引发的任何异常都将丢失。

这是通过解释 - 你猜对了 - 斯蒂芬·克利里,在this StackOverflow answer.

相关问题