泛型和反射

来源:互联网 发布:云计算的分类有哪些 编辑:程序博客网 时间:2024/05/19 13:29

一、概念

泛型允许程序员在代码中将变量或参数的类型,先用[类型占位符]来代替,等到允许的时候再根据传入的[类]来代替

泛型是指带类型参数的类,而不是参数本身。

类、方法、结构、接口都可定义为泛型

可以定义多个参数  public class Person<T1,T2,...>

实例化一个引用参数类型的泛型,它的内存分配的大小是一样的;实例化一个值参数类型的泛型,它的内存分配的大小是不同的



1、泛型类

语法:

定义:public class List<T,F>{}

调用:List<T,F> list=new List<T,F>()


继承

继承一个泛型类的时候,必须为其传递泛型参数


约束

public class List<T>where T:new(){}

约束T的实例必须包含一个无参的构造函数


2、泛型方法

public void Test<k>(){}
三种用法:当方法参数、当返回值、在方法中实例化

二、反射

1、主要方法
            //获取当前程序集对象集合           // Assembly[] ass = AppDomain.CurrentDomain.GetAssemblies();            //**************************反射获取成员            //1、获取当前正在运行的程序集( Assembly)对象            Assembly ass = this.GetType().Assembly;            //2、获取程序集中Dog类的类型(Type)对象            Type tDog = ass.GetType("反射.Dog");            //3、获取Dog类的name字段对象            FieldInfo finfo = tDog.GetField("name");            //4、获取Dog类的方法            MethodInfo minfo = tDog.GetMethod("ShootHi");            //**************************反射创建成员            //5、根据Dog的Type对象,实例化一个Dog对象            Dog d1 = Activator.CreateInstance(tDog) as Dog;            //6、使用Dog类的name字段对象,为d2实例的name字段赋值            finfo.SetValue(d1, "小白");            //7、使用Dog类的ShoutHi方法对象,执行d2实例的ShoutHi方法            string strRes = minfo.Invoke(d1, null).ToString();
获取类对象
    Assembly ass = this.GetType().Assembly;            //通过类全名            Type tDog = ass.GetType("反射.Dog");            //获取当前程序集所有的公共的类            Type[] types = ass.GetExportedTypes();            //通过程序集获取所有的类型            Type[] typeAll = ass.GetTypes();            //通过类 直接获取对象            Type t2 = typeof(Dog);            //通过对象来获取类型对象            Type t3 = this.GetType();            Dog d3 = new Dog();            Type t4 = d3.GetType();

2、调用第三方程序集类
using System;using System.Collections.Generic;using System.ComponentModel;using System.Data;using System.Drawing;using System.Linq;using System.Text;using System.Threading.Tasks;using System.Windows.Forms;using System.Reflection;namespace 记事本{    public partial class Form1 : Form    {        public Form1()        {            InitializeComponent();        }        private void Form1_Load(object sender, EventArgs e)        {            MakeBtnByDLL(); ;        }        //读取程序集文件,并生成插件按钮        public void MakeBtnByDLL()        {            //1.加载路径            string strAssPath = this.GetType().Assembly.Location;            //2.获取程序集所在文件夹,并专成插件文件夹的路径            string strDirPath = System.IO.Path.GetDirectoryName(strAssPath) + "\\plugs";            //3.扫描插件文件夹里面所有的程序集文件,获取dll            string[] strDLLpaths = System.IO.Directory.GetFiles(strDirPath, "*.dll");            //4.遍历程序集文件路径并加载程序及到内存中            foreach (string strDll in strDLLpaths)            {                //4.1根据路径加载程序及文件到内存中                Assembly ass = Assembly.LoadFrom(strDll);                //4.2判断程序集中是否有插件类                //4.2.1或去插件程序集里的公有类                Type[] types = ass.GetExportedTypes();                //重要:获取插件接口类型对象                Type plugType = typeof(记事本插件interface.IPlug);                //4.2.2循环遍历插件程序集里的类型,判断是否实现了记事本插件接口                foreach (Type t in types)                {                    //4.2.3判断t是否 实现了接口IPlug                    if (plugType.IsAssignableFrom(t))                    {                        //重要:根据插件类型,创建插件类对象,并专程接口对象同一调用                        记事本插件interface.IPlug iplugObj = Activator.CreateInstance(t) as 记事本插件interface.IPlug;                        //4.3创建插件按钮                        ToolStripMenuItem menuItem = new ToolStripMenuItem(t.Name);                        this.tmsMenuItem.DropDownItems.Add(menuItem);                        //位所有按钮的点击事件都绑定同一个方法                        menuItem.Click += menuItem_Click;                        //将接口对象存入按钮的tag属性                        menuItem.Tag = iplugObj;                    }                }            }        }        void menuItem_Click(object sender, EventArgs e)        {            ToolStripMenuItem menuItem = sender as ToolStripMenuItem;            //从按钮中取出对应的插件对象            记事本插件interface.IPlug iplug = menuItem.Tag as 记事本插件interface.IPlug;            //调用插件对象的处理文字方法,并重新设置给文本框            textBox1.Text = iplug.ProcessText(textBox1.Text);        }    }}
第三方dll文件放置于程序执行路径的plugs内


三、特性/标签


作用:使程序可以动态获取类中的属性,注释等
运行时给程序员看的
0 0
原创粉丝点击