统一更新来自不同线程的变量

时间:2016-11-25 19:59:47

标签: c# .net multithreading unity3d mono

我开始学习一些统一性,我对多线程有一个快速的问题。

我有一个包含datamodel类实例的类。该类的主要功能是异步获取远程资源并更新datamodel类。然后在update函数中读取datamodel类并将其写入游戏对象中的某些文本。

无论如何,我担心它可能会导致一些与多线程相关的问题,因为我的异步更新类可能会在更新函数导致竞争条件的同时运行。我是否必须在互斥锁中包装对类的访问权限?

class Data {
    public int Number { get; set; }
    public string Name { get; set; }
}

class Network : MonoBehaviour {
    private Data d;

    public void Start() {
        // setting up handler to async fetch data and call provided callback
        Networking.GetData(s => ParsePayload(s));
    }

    private void ParsePayload(string payload) {
        d = JsonConvert.DeserializeObject<Data>(payload);
    }

    public void Update() {
        var label = GameObject.Find("textObject").GetComponent<Text>();
        label.Text = d.Name;
    }
}

我在这方面是对的还是团结处理这个问题呢?

thx任何建议!

1 个答案:

答案 0 :(得分:2)

  

我在这方面是对的还是团结处理这个问题呢?

你是对的。它可能会导致一些问题,Unity会自己处理这个问题。您有责任确保一次只有一个线程可以访问d变量。有几种方法,但使用lock关键字可以实现此目的。

由于d功能更新ParsePayload并在Update函数中访问,因此您必须在两个函数中使用lock关键字。

另一个不相关的问题是GameObject.Find("textObject")。这应该在Start()函数中完成并保存到变量中。不要在每帧的更新功能中这样做。

class Network : MonoBehaviour
{
    private Data d;
    Text label;

    private System.Object threadLocker = new System.Object();

    public void Start()
    {
        label = GameObject.Find("textObject").GetComponent<Text>();

        // setting up handler to async fetch data and call provided callback
        Networking.GetData(s => ParsePayload(s));
    }

    private void ParsePayload(string payload)
    {
        lock (threadLocker)
        {
            d = JsonConvert.DeserializeObject<Data>(payload);
        }
    }

    public void Update()
    {
        lock (threadLocker)
        {
            label.text = d.Name;
        }
    }
}