【问题标题】:My helper function is throwing errors when I try to return a string from a context object [closed]当我尝试从上下文对象返回字符串时,我的辅助函数抛出错误 [关闭]
【发布时间】:2020-10-27 17:52:26
【问题描述】:

我有一个控制器,需要使用我制作的电子邮件界面向玩家发送电子邮件。

在邮件中,我需要向玩家展示他们遇到的怪物。

我正在尝试创建一个返回怪物名称的小辅助函数。

你可以在这里看到它:

    private async string GetMonsterTypeName(long id)
    {
        var monsterType = _context.MonsterTypes.FindAsync(id);
        return monsterType.Name;
    }

但 Visual Studio 2019 现在告诉我应该使方法同步。

但是,当我这样做时,我收到一条错误消息:

“ValueTask”不包含“Name”的定义,并且没有可访问的扩展方法“Name”接受“ValueTask”类型的第一个参数

但我的模型 MonsterTypes.cs 确实包含一个名为“Name”的字符串属性。

所以我不确定如何解决这个问题。

请问我该怎么做才能做到这一点?

这是我的更新后的代码,带有建议的修改:

    private async Task<string> GetMonsterTypeName(long id)
    {
        var monsterType = await _context.MonsterTypes.FindAsync(id);

        return monsterType.Name;
    }

谢谢你

【问题讨论】:

  • await _context.MonsterTypes.FindAsync(id);?
  • 返回签名应该是async Task&lt;string&gt;
  • @PanagiotisKanavos 谢谢你,但那还会返回怪物的名字吗?
  • 代码有两个错误。你需要修复它们

标签: c# entity-framework-core asp.net-core-webapi


【解决方案1】:

方法应该是:

private async Task<string> GetMonsterTypeName(long id)
{
    var monsterType = await _context.MonsterTypes.FindAsync(id);
    return monsterType.Name;
}

async 不会使方法异步,它允许您使用await 等待已经异步的操作,例如FindAsync,而不会阻塞当前的执行上下文。

异步方法应返回TaskValueTask。该任务是一个承诺,一个值将在未来的某个时间可用。要获得该值,您需要使用await 等待操作完成。

另一方面,当你只想要它的名字时,为什么要加载整个怪物呢?当您只需要一个简单的SELECT Name 时,FindAsync 等效于SELECT *

在这种情况下最好写:

private async Task<string> GetMonsterTypeName(long id)
{
    var monsterType = await _context.MonsterTypes
                                    .Where(m=>m.Id==id)
                                    .Select(m=>m.Name)
                                    .SingleOrDefaultAsync();
    return monsterType;
}

【讨论】:

  • 我明白了……这确实清除了该辅助函数中的错误。但是,当我尝试将该值发送到我的电子邮件函数时,我得到这个:无法从 'System.Threading.Tasks.Task' 转换为 'string' 因为我的电子邮件函数需要一个字符串作为怪物而不是任务。
  • 你使用await 得到结果了吗?这与问题代码的错误相同 - 尝试在不等待的情况下读取结果
  • 谢谢,是的,我确实添加了等待...我在原始问题中添加了改进的功能
  • 你没有发布你是如何调用这个方法的。你使用var name=await GeMonserTypeName(42); var name=GetMonsterTypeName(42)吗?我怀疑你在调用方法时没有使用await
  • @ 是的,我没有使用 await...它现在可以正常工作,并且零错误。谢谢!
【解决方案2】:

您需要为异步方法添加等待: var monsterType = await _context.MonsterTypes.FindAsync(id);

【讨论】:

    【解决方案3】:

    您已将函数声明为异步,但您没有等待任何内容:

    private async string GetMonsterTypeName(long id)
    {
        var monsterType = await _context.MonsterTypes.FindAsync(id); <-- Add await here.
        return monsterType.Name;
    }
    

    规则是,如果你用async装饰一个函数,那么你应该在函数的某处使用await

    【讨论】:

      猜你喜欢
      • 2019-10-29
      • 1970-01-01
      • 2020-03-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-02-20
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多