c# 反射用法及效率對(duì)比
反射實(shí)例化類(lèi)
public class Person { public string Name { get; set; } public Person(string name) { this.Name = name; } public string Say(string msg) { return $"{Name}: {msg}"; } } class Program { // 測(cè)試次數(shù) const int count = 10000000; static void Main(string[] args) { CreateInstance0(); CreateInstance1(); CreateInstance2(); CreateInstance3(); CreateInstance4(); Console.Read(); } static void CreateInstance0() { Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { Person person = new Person("張三"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - new"); } static void CreateInstance1() { Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { object person = Activator.CreateInstance(typeof(Person), "張三"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - Activator.CreateInstance"); } static void CreateInstance2() { Assembly assembly = Assembly.GetExecutingAssembly(); Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { Person obj = (Person)assembly.CreateInstance("ConsoleTest.Person", true, BindingFlags.Default, null, new object[] { "張三" }, null, null); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - Assembly.CreateInstance"); } static void CreateInstance3() { Assembly assembly = Assembly.GetExecutingAssembly(); Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { Type type = assembly.GetType("ConsoleTest.Person"); object person = Activator.CreateInstance(type, "張三"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - Assembly.CreateInstance1"); } static void CreateInstance4() { Assembly assembly = Assembly.GetExecutingAssembly(); Stopwatch watch = new Stopwatch(); watch.Start(); Type type = assembly.GetType("ConsoleTest.Person"); for (var i = 0; i < count; i++) { object person = Activator.CreateInstance(type, "張三"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - Assembly.CreateInstance2"); } }
- 通過(guò)反射實(shí)例化對(duì)象,要比直接 new 要慢 50 倍左右
- assembly.CreateInstance 要比 Activator.CreateInstance 慢,主要的性能損耗在 Assembly.GetType
反射調(diào)用類(lèi)的方法
class Program { // 測(cè)試次數(shù) const int count = 10000000; static void Main(string[] args) { InvokeMethod0(); InvokeMethod1(); InvokeMethod2(); InvokeMethod3(); InvokeMethod4(); Console.Read(); } static void InvokeMethod0() { Person person = new Person("張三"); Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { string name = person.Say("Hello World!"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - 直接調(diào)用"); } static void InvokeMethod1() { Person person = (Person)Activator.CreateInstance(typeof(Person), "張三"); Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { string name = person.Say("Hello World!"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - 反射緩存類(lèi)調(diào)用"); } static void InvokeMethod2() { Person person = (Person)Activator.CreateInstance(typeof(Person), "張三"); MethodInfo method = typeof(Person).GetMethod(nameof(Person.Say), new Type[] { typeof(string) }); Func<string, string> func = (Func<string, string>)method.CreateDelegate(typeof(Func<string, string>), person); Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { string result = func("Hello World!"); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - 使用反射創(chuàng)建出來(lái)的委托調(diào)用"); } static void InvokeMethod3() { Person person = (Person)Activator.CreateInstance(typeof(Person), "張三"); MethodInfo method = typeof(Person).GetMethod(nameof(Person.Say), new Type[] { typeof(string) }); object[] parameters = new object[] { "Hello World!" }; Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { string name = (string)method.Invoke(person, parameters); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - 使用反射得到的方法緩存調(diào)用"); } static void InvokeMethod4() { Person person = (Person)Activator.CreateInstance(typeof(Person), "張三"); object[] parameters = new object[] { "Hello World!" }; Stopwatch watch = new Stopwatch(); watch.Start(); for (var i = 0; i < count; i++) { string result = (string)(typeof(Person).GetMethod(nameof(Person.Say))?.Invoke(person, parameters)); } watch.Stop(); Console.WriteLine($"{watch.Elapsed} - 直接使用反射調(diào)用"); } }
- 反射得到實(shí)例后調(diào)用方法和直接調(diào)用方法效率一樣
- 緩存反射方法調(diào)用和直接使用反射調(diào)用都非常耗效率
以上就是c# 反射用法及效率對(duì)比的詳細(xì)內(nèi)容,更多關(guān)于c# 反射的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
使用C#驗(yàn)證PDF數(shù)字簽名有效性的方法示例
數(shù)字簽名作為PDF文檔中的重要安全機(jī)制,不僅能夠驗(yàn)證文件的來(lái)源,還能確保文件內(nèi)容在傳輸過(guò)程中未被篡改,本文將詳細(xì)介紹如何使用免費(fèi).NET控件通過(guò)C#驗(yàn)證PDF簽名的有效性以及驗(yàn)證PDF文檔是否被修改,需要的朋友可以參考下2024-07-07WPF實(shí)現(xiàn)背景燈光隨鼠標(biāo)閃動(dòng)效果
這篇文章主要為大家詳細(xì)介紹了WPF實(shí)現(xiàn)背景燈光隨鼠標(biāo)閃動(dòng)效果,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2020-08-08C# ListView 點(diǎn)擊表頭對(duì)數(shù)據(jù)進(jìn)行排序功能的實(shí)現(xiàn)代碼
這篇文章主要介紹了C# ListView 點(diǎn)擊表頭對(duì)數(shù)據(jù)進(jìn)行排序功能的實(shí)現(xiàn)代碼,需要的朋友可以參考下2017-04-04C#調(diào)用C++使用C++/CLI的實(shí)現(xiàn)
在C#開(kāi)發(fā)過(guò)程中,我們可能會(huì)遇到需要調(diào)用Windows API 或是第三方庫(kù)的場(chǎng)景,本文主要介紹了C#調(diào)用C++使用C++/CLI的實(shí)現(xiàn),具有一定的參考價(jià)值,感興趣的可以了解一下2024-03-03C#中判斷一個(gè)集合是否是另一個(gè)集合的子集的簡(jiǎn)單方法
本文介紹利用C#中內(nèi)置的系統(tǒng)函數(shù)判斷一個(gè)集合是否是一個(gè)集合的子集的方法,此方法代碼量極少,分享給大家。2016-04-04詳解MongoDB for C#基礎(chǔ)入門(mén)
本篇文章主要介紹了MongoDB for C#基礎(chǔ)入門(mén),具體介紹了c#中關(guān)于對(duì)MongoDB的連接,插入,查詢(xún)等,有需要的可以了解一下。2016-12-12C#實(shí)現(xiàn)航班查詢(xún)及預(yù)訂功能
這篇文章給大家介紹利用C#完成航班機(jī)票信息查詢(xún),航班機(jī)票預(yù)定等功能。代碼簡(jiǎn)單易懂,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友參考下吧2018-02-02