C# Unity3D协同程序和lambda回调,安全性

C# Unity3D协同程序和lambda回调,安全性,c#,unity3d,lambda,C#,Unity3d,Lambda,调用在协同程序中声明的System.Action安全吗 IEnumerator MyCoroutine(){ bool myBool = true; System.Action action = ()=>{myBool=false;} StartCoroutine (MyOtherCoroutine(action));//just launch and forget about it } IEnumerator MyOtherCoroutine(Sys

调用在协同程序中声明的System.Action安全吗

IEnumerator MyCoroutine(){
     bool myBool = true;
     System.Action action = ()=>{myBool=false;}

     StartCoroutine (MyOtherCoroutine(action));//just launch and forget about it
 }

 IEnumerator MyOtherCoroutine(System.Action dangerous_callback){
     yield return null;
     yield return null;//skip several frames
     yield return null;
     dangerous_callback.Invoke();//will cause problems? The owner coroutine (and it's myBool) is no longer on stack
 }
我关心的是在第一个协同程序中分配的
myBool
<代码>myothercorroutine不会等到
myothercorroutine
完成。我可以看到这个系统。操作不会被收集,因为它确实仍然被
myothercorroutine
引用,但是
myocroutine
(操作修改的布尔变量)应该已经被释放了

但这似乎是一个可能的内存泄漏,这可能是不可能的 以后再抓?只是问问用它是否合适

没有内存泄漏。这样做完全没问题,如果您需要在一个协程函数中进行回调,也可以这样做。请记住,这是C语言,在C语言中创建内存泄漏比使用C++更困难,除非你滥用Unity的API,这些API可能在本地(C++)方面造成内存泄漏,但这里不是这样。 尽管如此,在调用
操作之前,您应该先检查
操作是否为
null
,否则可能会出现代码中的一些问题

if (dangerous_callback != null)
    dangerous_callback.Invoke();

您是否遇到了问题,或者您是否询问这样做是否合适?我认为在协同路由中使用回调比较方便,因为不可能使用“ref”或“out”参数。但这似乎是一个可能的内存泄漏,以后可能无法捕获?只是问问用它是否合适,谢谢!这真的很奇怪,因为myBool直接属于MyCoroutine,所以我假设操作会尝试访问一些已取消分配的内存。我一直认为它们是一旦到达}就会从执行堆栈中删除的函数。因此,在c#中,在调用回调之前,将保留此原始协同程序?
操作
是一个
委托
,它是一个。当您将它传递给另一个协程函数时,GC将允许它一直存在,直到该协程函数存在为止。如果在任何地方都有它的引用,它将永远不会被释放。当执行
myothercorroutine
时,不存在对它的引用,因此现在可以由GC收集它。很抱歉这么固执:D但是在第一个corroutine中分配的myBool呢<代码>myothercorroutine
不会等到
myothercorroutine
完成。我可以看到该系统。操作不会被收集,因为它确实仍然被
myothercorroutine
引用,但是
myocroutine
(操作修改其布尔变量)应该已经被释放?没问题。来自C++的C语言使用时会遇到很多问题。“MyCustomer(操作修改其布尔变量)应该已被释放?”否。由于它在
Action
引用类型或
Action
变量中被引用,编译器将
myBool
变量移动到助手类中。见下文。因为您使用了lambda,所以它会创建一个闭包。我想补充一点,您可以使用null传播运算符在一行中编写它:
hazardous_callback?.Invoke()