You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C#非async方法如何确保LatestDate变量更新后再执行后续代码

问题核心原因

  • 你在同步方法中使用了await语法,但方法本身未标记async,本身就存在编译错误
  • 调用Wait()阻塞主线程会触发死锁:Firebase异步任务完成后需要切回Unity主线程执行回调,但主线程已经被Wait()阻塞等待任务结束,导致回调永远无法执行,latestDate永远停留在初始值0,严重时直接触发程序崩溃

解决方案1:使用async/await(推荐)

Unity 2018+ 都支持原生async/await语法,直接修改方法返回值为Task<bool>即可安全等待异步执行,不会阻塞主线程:

// 方法标记async,返回值改为Task<bool>
public async Task<bool> CheckWatchConnection()
{
    var latestDate = 0;
    var now = DateTimeOffset.Now.ToUnixTimeMilliseconds();
    bool connected = false;

    DatabaseReference lastHistoryEntry = DBreference.Child("users").Child(User.UserId).Child("History");
    var query = lastHistoryEntry.OrderByKey().LimitToLast(1); 

    // 直接await异步任务,主线程不会阻塞
    var snapshot = await query.GetValueAsync();
    if (snapshot.Exists)
    {
        latestDate = int.Parse(snapshot.Child("Date").Value.ToString());
        long diff = now - latestDate;
        connected = diff < 10;
    }
    return connected;
}

调用方法时也使用await接收结果:

// 调用处示例,Unity生命周期方法也可标记async void
private async void Start()
{
    bool isConnected = await CheckWatchConnection();
    // 拿到结果后执行后续逻辑
    Debug.Log($"连接状态:{isConnected}");
}

解决方案2:回调模式(适配无法修改方法签名的场景)

如果不能修改原方法的返回类型,就放弃同步返回值,改用回调委托接收结果:

// 增加回调参数,异步任务完成后触发回调
public void CheckWatchConnection(Action<bool> onComplete)
{
    var now = DateTimeOffset.Now.ToUnixTimeMilliseconds();
    DatabaseReference lastHistoryEntry = DBreference.Child("users").Child(User.UserId).Child("History");
    var query = lastHistoryEntry.OrderByKey().LimitToLast(1); 

    query.GetValueAsync().ContinueWith(task => 
    {
        if (task.IsFaulted || !task.Result.Exists)
        {
            // 错误或无数据时回调返回false
            onComplete?.Invoke(false);
            return;
        }
        int latestDate = int.Parse(task.Result.Child("Date").Value.ToString());
        long diff = now - latestDate;
        bool connected = diff < 10;
        
        // 如果回调中需要操作Unity UI/组件,需要把回调抛到主线程执行
        // 可直接用UnityMainThreadDispatcher工具类,或自己实现主线程任务队列
        UnityMainThreadDispatcher.Instance.Enqueue(() => onComplete?.Invoke(connected));
    });
}

调用方式:

CheckWatchConnection(isConnected => 
{
    // 此处拿到结果执行后续逻辑
    Debug.Log($"连接状态:{isConnected}");
});

内容的提问来源于stack exchange,提问作者Thekra

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.24 08:06:03