.NET C# 三種實例化一個類的方式的性能比較


本文內容

  • 實例化一個類的方式
  •     用 New 關鍵字實例化一個類
  •     用 Activator 實例化一個類
  •     用 Assembly 實例化一個類
  • 性能比較
  •     環境
  •     比較
  •     分析
  •     代碼

 

在開發應用程序時,能夠動態實例化一個類很有用。給出類的一個字符串名稱,就能夠創建這個類的一個實例。若這些需要實例化的類都繼承同一個接口(如本例的 IPerson),那么實例化的 object 類型轉換后可以賦值給這個接口。這很方便。否則,就得用 swtich-case 語句(估計會很長)。

那么,接下來的問題,實例化一個類的性能如何。

之前,我用 Assembly 較多,寫本文后,發覺好像不妥。

 

    實例化一個類的方式


    • 用 New 關鍵字實例化一個類

    New 關鍵字用於創建對象和調用構造函數。是實例化一個類最常見的方式。

    • 用 Activator 實例化一個類

    Activator 用以在本地或從遠程創建對象類型,或獲取對現有遠程對象的引用。其 CreateInstance 方法創建在程序集中定義的類型的實例。

    • 用 Assembly 實例化一個類

    Assembly 表示一個程序集,它是一個可重用、無版本沖突並且可自我描述的公共語言運行庫應用程序構造塊。該類可以加載程序集、瀏覽程序集的元數據和構成部分、發現程序集中包含的類型以及創建這些類型的實例。

    加載程序集的推薦方式是使用 Load 方法。GetType 方法可用於在程序集中搜索特定類型。CreateInstance 方法可用於在程序集中搜索和創建類型的實例。

    本文通過這三種方式來創建一個類的實例。

     

    性能比較

    環境

    • VS 2008 .NET Framework 3.5
    • Intel CPU Duo  T5450 1.66GHz
    • Memory 2G
    比較

    假設,Demo 中使用的類都在同一個程序集。

    using System;
     
    namespace InstancePerformance
    {
        class Program
        {
            static void Main(string[] args)
            {
                Console.WriteLine("實例化一個類的性能比較(單位:毫秒)");
                Console.Write("                    ");
                for (int i = 1; i <= 10; i++)
                    Console.Write("{0:G}", i.ToString().PadLeft(5));
                Console.Write("\n");
                // New Key
                Console.Write("InstanceByNew".PadRight(20));
                for (int i = 1; i <= 10; i++)
                    InstanceByNewKey.Create();
                Console.Write("\n");
                // Activator
                Console.Write("InstanceByActivator".PadRight(20));
                for (int i = 1; i <= 10; i++)
                    InstanceByActivator.Create();
                Console.Write("\n");
                // Assembly
                Console.Write("InstanceByAssembly".PadRight(20));
                for (int i = 1; i <= 10; i++)
                    InstanceByAssembly.Create();
                Console.Write("\n");
     
                Console.ReadKey();
            }
        }
    }

    實例化一個類的性能比較

    其中,

    • InstanceByNewKey.Create() 用 New 關鍵字實例化一個類;
    • InstanceByActivator.Create() 用 Activator 實例化一個類;
    • InstanceByAssembly.Create() 用 Assembly 實例化一個類。

    在“代碼”小節是這三個方法的實現代碼。

    • 為了便於測試,時間不至於小得可憐,以上每個方法實例化十萬次,也就是創建十萬個對象。
    • 為了便於比較,對以上每個方法都調用 10 次。進行橫向和縱向比較。

     1

    分析

    由上圖可以看出,用 Activator 實例化一個類最快;其次是用 New 關鍵字;最慢的是用 Assembly 實例化。Activator 比 用 New 都快。

    因此,若想動態實例化一個類,根據你的實際情況,盡量將需要實例化的類放在同一個程序集。

    代碼

    代碼段 1:IPerson 接口和 Person 類

    public class IPerson
    {
     
    }
    public class Person : IPerson
    {
        public string Name { get; set; }
     
        public Person()
        {
        }
        public Person(string name)
        {
            this.Name = name;
        }
    }

    代碼段 2:使用 New 關鍵字實例化

    public class InstanceByNewKey
    {
        /// <summary>
        /// 直接調用
        /// </summary>
        public static void Create()
        {
            IPerson person = null;
            Stopwatch watch = new Stopwatch();
            watch.Start();
            for (int i = 0; i < 100000; i++)
                person = new Person("My" + i);
            watch.Stop();
            Console.Write(watch.ElapsedMilliseconds.ToString().PadLeft(5));
        }
    }

    另外,若該代碼段寫成如下,是沒有必要的。其他代碼段類似。

    Stopwatch watch = new Stopwatch();
    watch.Start();
    for (int i = 0; i < 100000; i++)
        IPerson person = new Person("My" + i);
    watch.Stop();
    Console.Write(watch.ElapsedMilliseconds.ToString().PadLeft(5));

    代碼段 3:使用 Activator 實例化

    public class InstanceByActivator
    {
        /// <summary>
        /// 實例化反射
        /// </summary>
        public static void Create()
        {
            Type type = Type.GetType("InstancePerformance.Person");
            IPerson person = null;
     
            Stopwatch watch = new Stopwatch();
            watch.Start();
            for (int i = 0; i < 100000; i++)
            {
                object obj = Activator.CreateInstance(type);
                person = obj as IPerson;
            }
            watch.Stop();
            Console.Write(watch.ElapsedMilliseconds.ToString().PadLeft(5));
        }
    }

    代碼段 4:使用 Assembly 實例化

    public class InstanceByNewKey
    {
        /// <summary>
        /// 直接調用
        /// </summary>
        public static void Create()
        {
            IPerson person = null;
            Stopwatch watch = new Stopwatch();
            watch.Start();
            for (int i = 0; i < 100000; i++)
                person = new Person("My" + i);
            watch.Stop();
            Console.Write(watch.ElapsedMilliseconds.ToString().PadLeft(5));
        }
    }

    下載 Demo


    免責聲明!

    本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



     
    粵ICP備18138465號   © 2018-2025 CODEPRJ.COM