ChatGPT解决这个技术问题 Extra ChatGPT

异步等待返回任务

有人可以解释一下这对同步方法意味着什么吗?如果我尝试将方法更改为 async,那么 VS 会抱怨它。

这有效:

public Task MethodName()
{
     return Task.FromResult<object>(null);
}

这不起作用:

public async Task MethodName()
{
     return Task.FromResult<object>(null);
}

所以基本上我想知道这到底是什么意思:Task.FromResult<object>(null);

@LB 嗯,行得通!但如果我只是 return; 也可以......!
“不起作用”并没有很好地描述什么不起作用。您收到的错误信息是什么?
@JohnKoerner 我认为很明显编译器可能会给您带来与您尝试在 void 函数中返回值相同的错误。

b
bashis

async 方法与普通方法不同。您从 async 方法返回的任何内容都包含在 Task 中。

如果您没有返回值(void),它将被包裹在 Task 中,如果您返回 int,它将被包裹在 Task<int> 中,依此类推。

如果您的异步方法需要返回 int,您需要将该方法的返回类型标记为 Task<int>,并且您将返回普通的 int 而不是 Task<int>。编译器将为您将 int 转换为 Task<int>

private async Task<int> MethodName()
{
    await SomethingAsync();
    return 42;//Note we return int not Task<int> and that compiles
}

同样,当您返回 Task<object> 时,您的方法的返回类型应为 Task<Task<object>>

public async Task<Task<object>> MethodName()
{
     return Task.FromResult<object>(null);//This will compile
}

由于您的方法返回 Task,它不应该返回任何值。否则它不会编译。

public async Task MethodName()
{
     return;//This should work but return is redundant and also method is useless.
}

请记住,没有 await 语句的异步方法不是 async


对我来说,这种返回类型不起作用(我想我做错了什么)。示例静态异步 Task DoStuff() { ... = await SomeMethodAsync();返回“字符串值”; } .. var x = DoStuff();但是这个 x - 是“Task”类型,而不是“string”类型......为什么会这样?
@Prokurors 您还需要等待 DoStuff()。例如:var x = await DoStuff();
应该是 return await Task.FromResult<object>(null);
@sandeeptalabathula 等于返回 null
@ProfK Task.WhenAny 就是一个例子。
M
Major

使用 async 时需要使用 await 关键字,并且您的函数返回类型应该是通用的这是一个带有返回值的示例:

public async Task<object> MethodName()
{
    return await Task.FromResult<object>(null);
}

这是一个没有返回值的示例:

public async Task MethodName()
{
    await Task.CompletedTask;
}

阅读这些:

TPL:http://msdn.microsoft.com/en-us/library/dd460717(v=vs.110).aspx 和任务:http://msdn.microsoft.com/en-us/library/system.threading.tasks(v=vs.110).aspx

异步:http://msdn.microsoft.com/en-us/library/hh156513.aspx 等待:http://msdn.microsoft.com/en-us/library/hh156528.aspx


您可以直接返回 null 而不是等待虚拟任务。
@Lee,但是如果您这样做,编译器会抱怨(发出警告) async 方法将异步执行,并建议在方法中的某处使用 await 关键字。我建议只使用 return Task.FromResult((object)null); 并删除 async 关键字以减少编译器警告噪音。
是的,我尝试在任务中仅使用 return,但任务继续执行,因为 return 没有返回 Task
J
Jeremy Lakeman

添加 async 关键字只是简化状态机创建的语法糖。本质上,编译器获取您的代码;

public async Task MethodName()
{
     return null;
}

并将其变成;

public Task MethodName()
{
     return Task.FromResult<object>(null);
}

如果您的代码有任何 await 关键字,编译器必须采用您的方法并将其转换为一个类来表示执行它所需的状态机。在每个 await 关键字处,变量和堆栈的状态将保留在类的字段中,该类会将自己作为完成挂钩添加到您正在等待的任务中,然后返回。

当该任务完成时,您的任务将再次执行。因此,在方法的顶部添加了一些额外的代码来恢复变量的状态并跳转到代码的下一个板块。

有关血腥示例,请参见 What does async & await generate?

这个过程与编译器使用 yield 语句处理迭代器方法的方式有很多共同之处。


A
Adel Mourad

这是一个返回字符串类型的任务的任务(C# 匿名函数或换句话说,使用委托“Func”)

    public static async Task<string> MyTask()
    {
        //C# anonymous AsyncTask
        return await Task.FromResult<string>(((Func<string>)(() =>
        {
            // your code here
            return  "string result here";

        }))());
    }

在发布代码作为答案时,请对您演示的内容进行一些解释。在这种情况下,您正在为已有多个答案的旧问题添加答案。请添加一两句话来描述您的新答案所展示的内容,其他答案中尚未显示。我并不是说您的回答有任何问题,只是要求您通过将您在代码中显示的内容用语言表达出来来帮助他人。
a
abhiroop mukherjee

为了从异步方法获得正确的响应,您需要在调用这些任务方法时放置等待。这将等待将其转换回返回值类型而不是任务类型。

例如 var content = await StringAsyncTask ( where public async Task StringAsyncTask ())