【发布时间】:2017-04-23 00:50:28
【问题描述】:
我写了一个 Thread 帮助类,可以用来在 Unity 的主线程中执行一段代码。
这是功能蓝图:
public static void executeInUpdate(System.Action action)
完整的脚本真的很长,会使这篇文章变得不必要地冗长。你可以看到脚本助手类的其余部分here。
然后我可以像这样使用另一个 Thread 的统一 API:
UnityThread.executeInUpdate(() =>
{
transform.Rotate(new Vector3(0f, 90f, 0f));
});
问题是,当我使用在该委托之外声明的变量时,它会分配内存。上面的代码每帧分配 104 个字节。这是因为在该闭包中使用了 transform 变量。
现在这似乎没什么,但我每秒执行 60 次,我需要连接大约 6 个摄像头并在屏幕上显示图像。我不喜欢产生的垃圾量。
下面是我如何从相机下载图像并将其上传到 Unity 的示例。我每秒大约有 60 帧。 receiveVideoFrame() 函数在单独的线程上运行。它下载图像,将其发送到 Unity 的主 Thread,然后 Unity 将图像字节上传到 Texture2D。然后Texture2D 与RawImage 一起显示。由于UnityThread.executeInUpdate 而捕获闭包时会发生分配。
bool doneUploading = false;
byte[] videoBytes = new byte[25000];
public Texture2D videoDisplay;
void receiveVideoFrame()
{
while (true)
{
//Download Video Frame
downloadVideoFrameFromNetwork(videoBytes);
//Display Video Frame
UnityThread.executeInUpdate(() =>
{
//Upload the videobytes to Texture to display
videoDisplay.LoadImage(videoBytes);
doneUploading = true;
});
//Wait until video is done uploading to Texture/Displayed
while (!doneUploading)
{
Thread.Sleep(1);
}
//Done uploading Texture. Now set to false for the next run
doneUploading = false;
//Repeat again
}
}
如何使用闭包而不引起内存分配?
如果这不可能,还有其他方法吗?
我可以删除用于在主线程中执行代码的类,然后在主脚本中重新编写这些逻辑,但这会很麻烦而且很长。
【问题讨论】:
标签: c# multithreading unity3d delegates closures