博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
C#动态创建和动态使用程序集、类、方法、字段等(二)
阅读量:5323 次
发布时间:2019-06-14

本文共 3199 字,大约阅读时间需要 10 分钟。

 

  上一节讲了如何动态的创建,这一节就要讲创建了我们需要如何使用了,这当然也是非常重要的, 是吧。创建了动态类型但是又不使用,那创建它有什么用了。呵呵,今天我们就来一起学习动态使用动态创建的类型。

当然我们跟上一章一样要对这些动态类型的使用类型进行一些了解。

类:使用System.Type(任何时候都是反射出类型进行使用,难道不是吗?)

构造函数:System.Reflection.ConstructorInfo(发现类构造函数的属性并提供对构造函数元数据的访问权)

事件:System.Reflection.EventInfo(发现事件的属性并提供对事件元数据的访问权)

字段:System.Reflection.FieldInfo(发现字段属性并提供对字段元数据的访问权)

方法:System.Reflection.MemberInfo(获取有关成员属性的信息并提供对成员元数据的访问)

成员:System.Reflection.MemberInfo(获取有关成员属性的信息并提供对成员元数据的访问)

参数:System.Reflection.ParameterInfo(发现参数属性并提供对参数元数据的访问)

属性:System.Reflection.PropertyInfo (发现属性 (Property) 的属性 (Attribute) 并提供对属性 (Property) 元数据的访问)

同样这是一种延伸阅读,只是先对这些进行了解,如果不知道的话,可能对动态的使用类型就无法下手了。

今天我做了一个Demo,先上Demo吧,然后在来解释程序是如何执行的。

 

/动态创建的动态类型

        
public
 
static
 Type DynamicCreateType()
        {
            
//
动态创建程序集
            AssemblyName DemoName 
=
 
new
 AssemblyName(
"
DynamicAssembly
"
);
            AssemblyBuilder dynamicAssembly 
=
 AppDomain.CurrentDomain.DefineDynamicAssembly(DemoName, AssemblyBuilderAccess.RunAndSave);
            
//
动态创建模块
            ModuleBuilder mb 
=
 dynamicAssembly.DefineDynamicModule(DemoName.Name, DemoName.Name 
+
 
"
.dll
"
);
            
//
动态创建类MyClass
            TypeBuilder tb 
=
 mb.DefineType(
"
MyClass
"
, TypeAttributes.Public);
            
//
动态创建字段
            FieldBuilder fb 
=
 tb.DefineField(
"
myField
"
typeof
(System.String), FieldAttributes.Private);  
            
//
动态创建构造函数
            Type[] clorType 
=
 
new
 Type[] { 
typeof
(System.String) };
            ConstructorBuilder cb1 
=
 tb.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard, clorType);
            
//
生成指令
            ILGenerator ilg 
=
 cb1.GetILGenerator();
//
生成 Microsoft 中间语言 (MSIL) 指令
            ilg.Emit(OpCodes.Ldarg_0);
            ilg.Emit(OpCodes.Call, 
typeof
(
object
).GetConstructor(Type.EmptyTypes));
            ilg.Emit(OpCodes.Ldarg_0);
            ilg.Emit(OpCodes.Ldarg_1);
            ilg.Emit(OpCodes.Stfld, fb);
            ilg.Emit(OpCodes.Ret);
            
//
动态创建属性
            PropertyBuilder pb 
=
 tb.DefineProperty(
"
MyProperty
"
, PropertyAttributes.HasDefault, 
typeof
(
string
), 
null
);
            
//
动态创建方法
            MethodAttributes getSetAttr 
=
 MethodAttributes.Public 
|
 MethodAttributes.SpecialName;
            MethodBuilder myMethod 
=
 tb.DefineMethod(
"
get_Field
"
, getSetAttr, 
typeof
(
string
), Type.EmptyTypes);
            
//
生成指令
            ILGenerator numberGetIL 
=
 myMethod.GetILGenerator();
            numberGetIL.Emit(OpCodes.Ldarg_0);
            numberGetIL.Emit(OpCodes.Ldfld, fb);
            numberGetIL.Emit(OpCodes.Ret);
            
//
使用动态类创建类型
            Type classType 
=
 tb.CreateType();
            
//
保存动态创建的程序集 (程序集将保存在程序目录下调试时就在Debug下)
            dynamicAssembly.Save(DemoName.Name 
+
 
"
.dll
"
);
            
//
创建类
            
return
 classType;
        }

 

 

执行的主要方法

static
 
void
 Main(
string
[] args)
{
    
//
动态创建的类类型
    Type classType 
=
 DynamicCreateType();
    
//
调用有参数的构造函数
    Type[] ciParamsTypes 
=
 
new
 Type[] { 
typeof
(
string
) };
    
object
[] ciParamsValues 
=
 
new
 
object
[] { 
"
Hello World
"
 };
    ConstructorInfo ci 
=
 classType.GetConstructor(ciParamsTypes);
    
object
 Vector 
=
 ci.Invoke(ciParamsValues);
    
//
调用方法
    
object
[] methedParams
=
new
 
object
[]{};
    Console.WriteLine(classType.InvokeMember(
"
get_Property
"
, BindingFlags.InvokeMethod, 
null
, Vector, methedParams));
    Console.ReadKey();

 

这个程序首先调用DynamicCreateType()方法创建动态类型,这跟第一章里帖出来的如何创建的代码几乎是一样的,另外保存了动态创建的程序集,我创建了一个类,类里创建了有一个字段、有一个参数的构造函数、一个属性、有一个参数的构造函数和一个方法。用有参数的构造函数来初始化字段myField,然后调用get_Field方法返回myField字段的值。控制台程序显示“Hello World!!!”

后面还会继续介绍动态创建和动态使用类,如何创建复杂的方法,特别是中间语言(MSIL)的生成。

转载于:https://www.cnblogs.com/blogbai/archive/2012/09/28/2706706.html

你可能感兴趣的文章
jmeter接口测试之登录测试
查看>>
【CQOI2009】中位数
查看>>
ThinkPHP大写单字母函数
查看>>
ELK Stack (2) —— ELK + Redis收集Nginx日志
查看>>
ElasticSearch 2 (19) - 语言处理系列之故事开始
查看>>
NLTK的使用
查看>>
Java面试题之谈谈reactor模型
查看>>
win7下安装sdks
查看>>
通过maven profile 打包指定环境配置
查看>>
redis 存储时间区间的数据
查看>>
STM32F0库函数初始化系列:进入STOP模式,外部中断唤醒
查看>>
p1525 关押罪犯
查看>>
使用Html5shiv.js让ie支持html5
查看>>
DBA 优化法则
查看>>
用Python连接SQLServer抓取分析数据、监控 (pymssql)
查看>>
升级ruby后再安装cocodPod
查看>>
MySQL数据库8(十三)高级数据操作之select指令
查看>>
随心测试_Python Se_002<不同浏览器驱动>
查看>>
LeetCode 202. Happy Number
查看>>
【Codeforces Round #432 (Div. 2) A】 Arpa and a research in Mexican wave
查看>>