日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

匿名函数gc分析

發(fā)布時間:2023/12/15 编程问答 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 匿名函数gc分析 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

?測試一:使用member function創(chuàng)建action會產(chǎn)生gc,不管該函數(shù)是否訪問外部變量:

private System.Action memberAct = null;// gc 112Bprivate void ActionWithMethod(){memberAct = new System.Action(LocalMethod);}// gc 112B, if LocalMethod() is static, then no gcprivate void ActionWithMethod2(){memberAct = LocalMethod;}// no gcprivate void ActionWithMethod3(){System.Action act = memberAct;}private void LocalMethod(){foreach (var item in lst)Debug.Log(item);}

  ActionWithMethod和ActionWithMethod2是等效的,gc值如下所示:

  

  IL代碼也一摸一樣:

  

  所以將一個member function復制給一個action會產(chǎn)生gc,解決的辦法就是ActionWithMethod3,也就是用一個actin member緩存起來,然后將緩存的action member復制給新建的action,這樣只會產(chǎn)生一次gc:

如果將LocalMethod設(shè)置為static函數(shù),則ActionWithMethod2也不會產(chǎn)生gc: private static void LocalMethod(){}

  

?

測試二:使用匿名函數(shù),如果訪問了外部變量,也會產(chǎn)生gc;如果不訪問外部變量,則只產(chǎn)生一次gc

using System.Collections; using System.Collections.Generic; using UnityEngine; public class TestAnonymousFunctionGC : MonoBehaviour {private System.Action actMember = null;private int iMember = 1;public TestAnonymousFunctionGC(){}private void Update(){UnityEngine.Profiling.Profiler.BeginSample("*** AnoymousFunctionWithoutArg ***");AnoymousFunctionWithoutArg();UnityEngine.Profiling.Profiler.EndSample();
UnityEngine.Profiling.Profiler.BeginSample(
"*** AnoymousFunctionWithMemberArg ***");AnoymousFunctionWithMemberArg();UnityEngine.Profiling.Profiler.EndSample();
UnityEngine.Profiling.Profiler.BeginSample(
"*** AnoymousFunctionWithLocalArg1 ***");AnoymousFunctionWithLocalArg1();UnityEngine.Profiling.Profiler.EndSample();
UnityEngine.Profiling.Profiler.BeginSample(
"*** AnoymousFunctionWithLocalArg2 ***");AnoymousFunctionWithLocalArg2();UnityEngine.Profiling.Profiler.EndSample();
UnityEngine.Profiling.Profiler.BeginSample(
"*** AnoymousFunctionWithLocalArg3 ***");AnoymousFunctionWithLocalArg3();UnityEngine.Profiling.Profiler.EndSample();}// no gcprivate void AnoymousFunctionWithoutArg(){actMember = () => { };}// gc 112Bprivate void AnoymousFunctionWithMemberArg(){actMember = () =>{Debug.Log(iMember);};}// gc 129Bprivate void AnoymousFunctionWithLocalArg1(){bool bValue = true;actMember = () =>{Debug.Log(bValue);};}// gc 132Bprivate void AnoymousFunctionWithLocalArg2(){int iValue = 100;actMember = () =>{Debug.Log(iValue);};}// gc 136Bprivate void AnoymousFunctionWithLocalArg3(){int iValue = 1;int iValue2 = 2;actMember = () =>{Debug.Log(iValue);Debug.Log(iValue2);};} }

  

  同時還可以發(fā)現(xiàn),匿名函數(shù)引用的外部變量的個數(shù)會影響gc的值,為什么呢?來分析一波:

  

可以看到訪問外部變量的匿名函數(shù),會導致臨時對象的創(chuàng)建,這樣會導致gc,那位為什么每個臨時變量的gc值不一樣呢,我們來看一下這些臨時class的定義:

  

  可以看匿名函數(shù)所訪問的外部變量都會在臨時類里面創(chuàng)建一個拷貝,這樣每個類對象的大小就不一樣了。

  附上類型定義的完整代碼,前因后果一目了然:

public class TestAnonymousFunctionGC : MonoBehaviour {// Fieldsprivate Action actMember;private int iMember;// Methodspublic TestAnonymousFunctionGC(){this.actMember = null;this.iMember = 1;base..ctor();return;}[CompilerGenerated]private void <AnoymousFunctionWithMemberArg>b__5_0(){Debug.Log((int) this.iMember);return;}private void AnoymousFunctionWithLocalArg1(){<>c__DisplayClass6_0 class_;class_ = new <>c__DisplayClass6_0();class_.bValue = 1;this.actMember = new Action(class_.<AnoymousFunctionWithLocalArg1>b__0);return;}private void AnoymousFunctionWithLocalArg2(){<>c__DisplayClass7_0 class_;class_ = new <>c__DisplayClass7_0();class_.iValue = 100;this.actMember = new Action(class_.<AnoymousFunctionWithLocalArg2>b__0);return;}private void AnoymousFunctionWithLocalArg3(){<>c__DisplayClass8_0 class_;class_ = new <>c__DisplayClass8_0();class_.iValue = 1;class_.iValue2 = 2;this.actMember = new Action(class_.<AnoymousFunctionWithLocalArg3>b__0);return;}private void AnoymousFunctionWithMemberArg(){this.actMember = new Action(this.<AnoymousFunctionWithMemberArg>b__5_0);return;}private void AnoymousFunctionWithoutArg(){this.actMember = (<>c.<>9__4_0 != null) ? <>c.<>9__4_0 : (<>c.<>9__4_0 = new Action(this.<AnoymousFunctionWithoutArg>b__4_0));return;}private void Update(){Profiler.BeginSample("*** AnoymousFunctionWithoutArg ***");this.AnoymousFunctionWithoutArg();Profiler.EndSample();Profiler.BeginSample("*** AnoymousFunctionWithMemberArg ***");this.AnoymousFunctionWithMemberArg();Profiler.EndSample();Profiler.BeginSample("*** AnoymousFunctionWithLocalArg1 ***");this.AnoymousFunctionWithLocalArg1();Profiler.EndSample();Profiler.BeginSample("*** AnoymousFunctionWithLocalArg2 ***");this.AnoymousFunctionWithLocalArg2();Profiler.EndSample();Profiler.BeginSample("*** AnoymousFunctionWithLocalArg3 ***");this.AnoymousFunctionWithLocalArg3();Profiler.EndSample();return;}// Nested Types [Serializable, CompilerGenerated]private sealed class <>c{// Fieldspublic static readonly TestAnonymousFunctionGC.<>c <>9;public static Action <>9__4_0;// Methodsstatic <>c(){<>9 = new TestAnonymousFunctionGC.<>c();return;}public <>c(){base..ctor();return;}internal void <AnoymousFunctionWithoutArg>b__4_0(){return;}}[CompilerGenerated]private sealed class <>c__DisplayClass6_0{// Fieldspublic bool bValue;// Methodspublic <>c__DisplayClass6_0(){base..ctor();return;}internal void <AnoymousFunctionWithLocalArg1>b__0(){Debug.Log((bool) this.bValue);return;}}[CompilerGenerated]private sealed class <>c__DisplayClass7_0{// Fieldspublic int iValue;// Methodspublic <>c__DisplayClass7_0(){base..ctor();return;}internal void <AnoymousFunctionWithLocalArg2>b__0(){Debug.Log((int) this.iValue);return;}}[CompilerGenerated]private sealed class <>c__DisplayClass8_0{// Fieldspublic int iValue;public int iValue2;// Methodspublic <>c__DisplayClass8_0(){base..ctor();return;}internal void <AnoymousFunctionWithLocalArg3>b__0(){Debug.Log((int) this.iValue);Debug.Log((int) this.iValue2);return;}} }Collapse Methods

參考:https://blog.uwa4d.com/archives/Anonymous_heapmemory.html

?

Vector3.Equals函數(shù)會有g(shù)c:

// Vector3.Equeals有GC 28B {UnityEngine.Profiling.Profiler.BeginSample("*** Vector3.Equals ***");Vector3 dir1 = Vector3.one, dir2 = Vector3.one;var equals = dir1.Equals(dir2);UnityEngine.Profiling.Profiler.EndSample();}

?

?

總結(jié)

以上是生活随笔為你收集整理的匿名函数gc分析的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。