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

同时为多个线程调用Join

同时为多个线程调用Join

C#
浮云间 2021-06-24 18:14:35
我正在用 C# 为 Unity 编写一个脚本来读取来自多个来源的消息。我有一个函数ReadMessage,它接受一个端口字符串并返回一个字符串 ID 号。问题是,我有十几个不同的连接需要读取,并且消息在停止尝试并让代码继续之前有一个 10 毫秒的超时计时器。当我有十几个线程等待前一个线程完成加入时,这会导致帧速率降低。我的线程代码如下:string threadOneString= null;Thread ThreadOne;//Repeat for 11 more threadsvoid Update () {    ThreadOne = new Thread(        () =>        {            threadOneString = ReadMessage(someClass.port);        });    ThreadOne.Start();//Repeat for 11 more threads}void LateUpdate () {    ThreadOne.Join();    //Repeat for 11 more threads    UpdateClass(threadOneString);    //Repeat for 11 more threads    UpdateTextDisplay(); //Just updates a Unity Text object}还有我的ReadMessage代码,以防万一。private string ReadMessage(string port) //Change this name to ReadButtonPress    {        string fullMessage = "";        someStruct parsedMessage;        var timeout = new System.TimeSpan(0, 0, 0, 0, 10); // Less than 10 and it starts to miss most messages, ideally this would be a bit higher        string connectionString = PROTOCOL + CONTROLLER_IP + ":" +  port;        AsyncIO.ForceDotNet.Force();             using (var subSocket = new SubscriberSocket())        {            subSocket.Connect(connectionString);            subSocket.Subscribe("");            subSocket.TryReceiveFrameString(timeout, out fullMessage);            UnityEngine.Debug.Log("Message: " + fullMessage);            subSocket.Close();        }    // Some message parsing and checking...    return parsedMessage.someString;}我想做的,但我不知道是否可能,是同时为每个线程调用 Joins,而不是调用一个,等待,然后调用下一个。线程不相互交互,所以我希望这是可能的。如果没有,我将不胜感激另一个解决方案或建议。编辑:澄清正在发生的事情。当我只运行几个线程时,我的 FPS 为 65-70。当我运行所有 12 个线程时,我的 FPS 下降到 ~50 并且我有 60 FPS 的硬要求。
查看完整描述

3 回答

?
慕仙森

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

感谢这里的一些反馈,我不再每次更新都创建一个套接字。相反,我创建了套接字,Start()然后从类中的公共函数中读取我需要的内容。

不要做我所做的,并在每个 .bashrc 文件中重新创建完全相同的线程和套接字Update()。事后看来,这是一个非常糟糕的选择。


查看完整回答
反对 回复 2021-06-26
?
慕少森

TA贡献2019条经验 获得超9个赞

定义 ManualResetEvent 并在获得结果时发出信号,您可以使用 WaitHandle.WaitAny 最多等待 64 个等待句柄


查看完整回答
反对 回复 2021-06-26
?
精慕HU

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

改用任务,并将它们放入列表中。


var myTasks = new List<Task>();

Task allUpdateTasks;

...

void Update () {

    myTasks.Add(

        Task.Factory.StartNew(() =>

        {

            threadOneString = ReadMessage(someClass.port);

        }));

//Repeat for 11 more tasks


// Create a single tasks that will hold all tasks above.

allUpdateTasks = Task.WhenAll(myTasks);

}


void LateUpdate() {

    allUpdateTasks.Wait();

...

}


查看完整回答
反对 回复 2021-06-26
  • 3 回答
  • 0 关注
  • 216 浏览

添加回答

举报

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