程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> .NET網頁編程 >> C# >> C#入門知識 >> C#反射基礎知識和實戰應用

C#反射基礎知識和實戰應用

編輯:C#入門知識

C#反射基礎知識和實戰應用


首先來說一下什麼是反射?    反射提供了封裝程序集、模塊和類型的對象(Type類型)   可以使用反射動態的創建類型的實例,將類型綁定到現有對象,或從現有對象中獲取類型,然後,可以調用類型的方法或訪問其字段和屬性 。   總之,有了反射,以前很多實現不了的功能都可以實現。   下面先來寫一個小例子,體驗一下反射是怎麼一回事:   打開VS2010,新建一個控制台應用程序,在program.cs裡面寫代碼   首先引入命名空間:   using System.Reflection; 下如下代碼:            PropertyInfo len = typeof(string).GetProperty("Length");          string s = "Hello,reflection!";          int length = (int)len.GetValue(s, null);          Console.WriteLine(length.ToString()); 這裡通過反射獲取string的Length屬性,並通過調用PropertyInfo 的GetValues方法獲取屬性值,其中GetValues方法的原型如下:   public virtual object GetValue(object obj, object[] index); 第一個參數obj是擁有此屬性的類的實例,在這個例子中,為字符串s,s擁有Length屬性。   第二個參數為索引值,微軟解釋如下:   Optional index values for indexed properties. This value should be null for non-indexed properties.   一般情況下用null,大家可以自己深入研究一下。   GetValues方法返回的是object類型,所以必須強制轉換類型。       下面通過反射來獲取string的一個方法,看看方法是如何通過反射得到的,代碼如下:   string s = "Hello,reflection!"; MethodInfo method = typeof(string).GetMethod("Contains"); bool result = (bool)method.Invoke(s, new object[] { "Hello" }); Console.WriteLine(result); 其中,Invoke的方法定義如下:   public object Invoke(object obj, object[] parameters); 這個就很好理解了,第一個參數為擁有此方法的類的實例,還是為string實例s.   第二個參數就是一個object數組的參數。   這裡調用的是string中的Contains方法,判斷string中是否包含某個字符串。       下面通過反射來實例化一個string對象,代碼如下:        Type t = Type.GetType("System.String");          char[] para = new char[] { 'H', 'e', 'l', 'l', 'o' };          var o = Activator.CreateInstance(t, para);          Console.WriteLine(o); 這個跟獲取方法相似,唯一不同的就是string的構造方法參數是char[]數組,所以必須傳入符合的類型。這裡實例化了一個string,值為Hello。       看到這裡,你對反射已經有了初步的了解,下面開始進入實戰應用:   在解決方案上面點擊鼠標右鍵,添加項目,選中類庫,輸入名稱,添加一個類庫。   在類庫中添加Custom類,代碼如下:   復制代碼 using System; using System.Collections.Generic; using System.Linq; using System.Text;   namespace ReflectionDll {    public class Custom     {       public string Name { get; set; }       public string Address { get;set; }       public int Age { get; set; }       public DateTime BirthDay { get; set; }         public string GetInfo(string name = "",int age = 0)       {          if (name == "" && age == 0)          {             return "Custom Name: " + this.Name + ",Age: " + this.Age;          }          else          {             return "Custom Name: " + name + ",Age: " + age;          }       }    } } 復制代碼 這裡只聲明了幾個屬性和一個方法,供演示使用。寫好後編譯一下,在控制台項目裡面添加引用這個類庫(為了方便,否則每次編譯都要手動拷貝DLL到控制台項目下面),這樣VS會自動將生成的DLL拷貝到控制台debug目錄下,方便調用。下面開始使用反射來加載這個DLL,代碼如下:           string path = Environment.CurrentDirectory + "\\ReflectionDll.dll";          Assembly assem = Assembly.LoadFile(path);          Type customType = assem.GetType("ReflectionDll.Custom");          var custom = Activator.CreateInstance(customType); 注意了,這裡首先要獲取DLL的物理路徑,所以上面是否添加引用是無所謂的。有了路徑後,通過Assembly的LoadFile方法加載DLL,再獲取類的Type,注意GetType方法裡面的參數必須為類的全稱,及命名空間 + 類名,否則無法找到。   最後一行,創建了一個類的實例,類型為object類型。   下面來獲取Custom的所有屬性,代碼如下:   復制代碼  PropertyInfo[] propertys = customType.GetProperties();            Console.WriteLine("******************************");          foreach (PropertyInfo pro in propertys)          {             Console.WriteLine("PropertyName:" + pro.Name + "\n" +                "PropertyType:" + pro.PropertyType + "\n" +                "ClassName:" + pro.ReflectedType + "\n" +                "DLLName:" + pro.Module + "\n");          }          Console.WriteLine("******************************"); 復制代碼 通過調用GetProperties方法獲取所有屬性,保存到PropertyInfo[]數組中,然後遍歷數組輸出屬性值。   下面是各個屬性的含義:   Name                      屬性名稱   PropertyType          屬性數據類型   ReflectedType         所在的類的命名控件 + 類名   Module                  所在的DLL文件名稱       設置某個屬性的值,方法如下:        PropertyInfo p = customType.GetProperty("Name");      p.SetValue(custom, "CustomName",null); 是不是很容易啊。。。   下面來說一下,調用類的方法,和一些屬性。代碼如下:   復制代碼          MethodInfo _method = customType.GetMethod("GetInfo");          //顯示方法名稱          Console.WriteLine("Invoke method:" + _method.Name);          //顯示返回的數據類型          Console.WriteLine("Return type:" + _method.ReturnParameter);          ParameterInfo[] parameters =  _method.GetParameters();          foreach (ParameterInfo pa in parameters)          {             Console.WriteLine(pa.Name + pa.ParameterType + pa.Position + pa.Member);          }                    object[] paras = new object[] { "Jack",24 };            Console.WriteLine(_method.Invoke(custom, paras)); 復制代碼 同屬性一樣,參數可以通過GetParameters()來獲取,獲取的參數信息如下:   Name                參數名稱 ParameterType       參數數據類型 Position            參數的位置 Member              輸出所有參數   調用有參數的方法時,需要傳入參數,New一個object數組,將參數按順序寫入即可。  

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved