泛型+發射

一、泛型

協變與逆變:
協變(covariant),如果它保持了子類型序關係≦。該序關係是:子類型≦基類型。
逆變(contravariant),如果它逆轉了子類型序關係。
不變(invariant),如果上述兩種均不適用

  class Bird { }
  class Sparrow: Bird { }

  List<Bird> birdList3 = new List<Sparrow>().Select(c => (Bird)c).ToList();

  IEnumerable<Bird> birdList4 = new List<Bird>();
  IEnumerable<Bird> birdList5 = new List<Sparrow>();
  Func<Bird> func = new Func<Sparrow>(() => null);

二、反射

優點:動態
反射缺點: 程序複雜
          避開編譯器檢查
          性能問題

2.1 創建對象

2.1.1 加載程序集

//方法一:通過dll名稱加載程序集
 Assembly assembly = Assembly.Load("com.sunyopetical.MysqlHelper");
 //方法二:通過完整路徑加載
 Assembly assembly1 = Assembly.LoadFile(@"E:\高級進階\反射\bin\Debug\com.sunyopetical.MysqlHelper.dll");
 //方法三:通過完整名稱加載
Assembly assembly2 = Assembly.LoadFrom("com.sunyopetical.MysqlHelper.dll");

2.1.2 獲取數據庫中的所有的模塊

//獲取所有模塊
foreach (var item in assembly.GetModules())
{
      //獲取模塊完整路徑 FullyQualifiedName
     Console.WriteLine(item.FullyQualifiedName);
 }

2.1.2 獲取所有類型Type

//獲取程序集中所的類型
foreach (var item in assembly.GetTypes())
 {
 		//獲取類型的名稱
        Console.WriteLine(item.FullName);
 }

2.1.3 創建對象

//根據類型名,加載對應類型
Type type = assembly.GetType("com.sunyopetical.MysqlHelper.MySqlHelper");
//創建對象
object o = Activator.CreateInstance(type);
IDbHelper iDbHelper = (IDbHelper)o;
//執行方法
iDbHelper.Query();

2.2 工廠方法+XML文件動態加載

2.2.1 工廠類

public class Factory
    {
        private static string IDBHelperConfig = ConfigurationManager.AppSettings["IDBHelperConfig"];
        //com.sunyopetical.MysqlHelper,com.sunyopetical.MysqlHelper.MySqlHelper
        private static string DllName = IDBHelperConfig.Split(',')[0];
        private static string TypeName = IDBHelperConfig.Split(',')[1];
        public static IDbHelper CreateHelper()
        {

            //通過dll名稱加載程序集
            Assembly assembly = Assembly.Load(DllName);
            //通過完整路徑加載
            //Assembly assembly1 = Assembly.LoadFile(@"C:\Users\Administrator\Documents\visual studio 2015\Projects\高級進階\com.sunyopetical.MysqlHelper.dll");
            Type type = assembly.GetType(TypeName);
            object o = Activator.CreateInstance(type);
            IDbHelper iDbHelper = (IDbHelper)o;
            return iDbHelper;
        }

2.3 單例模式下的反射

2.3.1 反射調用構造函數

反射會破壞類的私有構造方法

{
	Assembly assembly = Assembly.Load("com.sunyopetical.MysqlHelper");
	Type type = assembly.GetType("com.sunyopetical.MysqlHelper.MySqlSingle_lazy");
	//反射會調用無參數的構造函數 true:公共或非公共默認構造函數可以匹配 false:只有公共默認構造函數可以匹配
	MySqlSingle_lazy pMySqlSingle_lazy = (MySqlSingle_lazy)Activator.CreateInstance(type, true);
	MySqlSingle_lazy pMySqlSingle_lazy2 = (MySqlSingle_lazy)Activator.CreateInstance(type, true);
}

//反射調用有參數的構造函數
{
     Assembly assembly = Assembly.Load("com.sunyopetical.MysqlHelper");
     Type type = assembly.GetType("com.sunyopetical.MysqlHelper.ReflectionTest");
       //反射調用有參數的構造函數
      Activator.CreateInstance(type, new object[] { 123, "123" });
      Activator.CreateInstance(type, new object[] { 123, 123 });
   }
   
//調用泛型函數
 {
      Assembly assembly = Assembly.Load("com.sunyopetical.MysqlHelper");
       //`2兩個參數的泛型
       Type type = assembly.GetType("com.sunyopetical.MysqlHelper.GenericClass`2");
       //反射調用泛型
       Type newType = type.MakeGenericType(new Type[] { typeof(int), typef(string) });
       Activator.CreateInstance(newType);
            }

2.3.1 反射調用函數

{
    Console.WriteLine("*************Reflection+Method***************");
    Assembly assembly = Assembly.Load("com.sunyopetical.MysqlHelper");
    Type type = assembly.GetType("com.sunyopetical.MysqlHelper.ReflectionTest");
    //反射調用有參數的構造函數
    //Activator.CreateInstance(type, new object[] { 123, "123" });
    //Activator.CreateInstance(type, new object[] { 123, 123 });
    object o = Activator.CreateInstance(type);
    //調用無參的方法
    //MethodInfo method2 = type.GetMethod("Show1");
    //method2.Invoke(o,null);
    ////調用帶參數的方法
    //MethodInfo method = type.GetMethod("Show2");
    //method.Invoke(o,new object[] { 1});
    //調用靜態的方法
    //MethodInfo method3 = type.GetMethod("Show3");
    //方式1
    //method3.Invoke(null, new object[] { "天天向上" });
    //方式2
    //method3.Invoke(o, new object[] { "好好學習" });

    //重載函數的反射
    MethodInfo method4 = type.GetMethod("Show4",new Type[] { });
    method4.Invoke(o, new object[] { });
    method4 = type.GetMethod("Show4", new Type[] { typeof(int) });
    method4.Invoke(o, new object[] {33});
    method4 = type.GetMethod("Show4", new Type[] { typeof(string) });
    method4.Invoke(o, new object[] { "oipoi" });
    //調用私有方法
    MethodInfo method5 = type.GetMethod("Show5", BindingFlags.Instance | BindingFlags.NonPublic);
    method5.Invoke(o, new object[] { "hhhhhh" });

    //調用泛型類、泛型方法
    Assembly assembly2 = Assembly.Load("com.sunyopetical.MysqlHelper");
    //`2兩個參數的泛型
    Type type2 = assembly2.GetType("com.sunyopetical.MysqlHelper.GenericDouble`1");
    //反射調用泛型
    Type newType2 = type2.MakeGenericType(new Type[] { typeof(int)});
    object o2 = Activator.CreateInstance(newType2);
    MethodInfo methodInfo = newType2.GetMethod("Show");
    if (methodInfo.IsGenericMethod)
    {
        MethodInfo newMethod = methodInfo.MakeGenericMethod(new Type[] { typeof(string), typeof(DateTime) });
        newMethod.Invoke(o2, new object[] { 1, "swq", DateTime.Now });
    }

    //反射+字段/屬性  ORM
    {
        Console.WriteLine("***********反射+字段/屬性 ************");

        Assembly assembly4 = Assembly.Load("com.sunyopetical.MysqlHelper");
     
        Type type4 = assembly4.GetType("com.sunyopetical.MysqlHelper.People");

        Type peopleType = typeof(People);
        object o4 = Activator.CreateInstance(peopleType);
        foreach (var item in peopleType.GetProperties())
        {
            Console.WriteLine(item.Name);//獲取字段名稱
            Console.WriteLine(item.GetValue(o4));//獲取字段屬性
            if (item.Name.Equals("Name"))
            {
                item.SetValue(o4, "hhh");
            }
            Console.WriteLine($"{type.Name}");

        }
        //GetFields()與GetProperties() 等價
        foreach (var item in peopleType.GetFields())
        {
            Console.WriteLine(item.Name);//獲取字段名稱
            Console.WriteLine(item.GetValue(o4));//獲取字段屬性
            if (item.Name.Equals("Name"))
            {
                item.SetValue(o4, "hhh");
            }
            Console.WriteLine($"{type.Name}");
        }

        Type typePeople = typeof(People);
        Type typePeopleDTO = typeof(PeopleDTO);
        object peopleDTO = Activator.CreateInstance(typePeopleDTO);
        foreach (var filed  in typePeopleDTO.GetFields())
        {

        }
    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章