为了账号安全,请及时绑定邮箱和手机立即绑定

Unity3d中的“await”如何不阻塞?

Unity3d中的“await”如何不阻塞?

C#
隔江千里 2023-08-20 15:39:46
这是我的代码using System;using System.Collections;using System.Threading.Tasks;using UnityEngine;public class NewMonoBehaviour : MonoBehaviour{    // Start is called before the first frame update    [SerializeField]    GameObject player;    void Start()    {    }    // Update is called once per frame    async void Update()    {        if (Input.GetKeyDown("space"))        {            Debug.Log("Start");            await Task.Delay(3000);            Debug.Log("End");        }        if (Input.GetKey(KeyCode.A))        {            player.transform.Translate(new Vector3(-1,0,0) * Time.deltaTime);        }        if (Input.GetKey(KeyCode.D))        {            player.transform.Translate(new Vector3(1,0,0) * Time.deltaTime);        }    }}当我按下空格键时,即使延迟尚未结束,我也可以左右移动。此外,我可以反复按空格键以获得StartStartStartEndEndEnd这就像我想要的那样,但我想了解为什么。我想这个方法中的所有内容都会被阻止,直到 Task.Delay 完成。
查看完整描述

2 回答

?
德玛西亚99

TA贡献1770条经验 获得超3个赞

你已经完成了async整个Update()方法。


async void Update()

{//whatever needs to be done in a frame}

渲染Update方法异步运行,这样 Unity 就不会等待它返回就继续执行。它继续调用Update()所有其他对象,执行其操作,渲染帧,直到async void Update()在同一对象上的下一帧上达到相同的效果。所以,它可以反应


if (Input.GetKey(KeyCode.A))

    {

        player.transform.Translate(new Vector3(-1,0,0) * Time.deltaTime);

    }

在后一帧上,即使前一帧Update()正在等待await Task.Delay(3000). 这就是您获得结果的原因。


顺便说一句,async void Update()恕我直言,这是一个坏主意,因为当各种Update()方法在意外的时间返回不同的值并在意外的时间修改变量时,您会得到意外的结果。我会保持Update()同步,并最终让它调用一个async可以满足您需要的方法。


查看完整回答
反对 回复 2023-08-20
?
精慕HU

TA贡献1845条经验 获得超8个赞

异步编程并使用基于任务的异步模式 (TAP)

基于 .NET 任务的异步模型由 Task 和 Task 类型以及 C# 中的 async 和await 关键字公开

我意识到理解这些文档并不总是那么容易;所以基本上发生的情况是,当您await在方法中时,返回值在调用中“保留” await Update()。一旦等待完成,调用者将收到该值,这将在调用树中向上级联。

重要的是每个单独的方法调用都变得异步。我认为它就像你给员工的工作卡。你可以不断地给他们新卡,每次他们完成工作时,他们都会把卡还给你,你就做你必须做的事。员工可能会选择先做简单的事情,这样您很可能会以不同的顺序取回卡片,但这并不重要。


查看完整回答
反对 回复 2023-08-20
  • 2 回答
  • 0 关注
  • 212 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信