热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

C#反射reflection

C#shanzm目录简介引入1.新建类库2.类库的使用3.反射反射实例1反射实例2反射实例3简介反射(reflection)是什么?在《精通C#》中是这么说的“反射就是一个运行库发





C#

shanzm



目录


  • 简介


  • 引入

    • 1.新建类库

    • 2. 类库的使用

    • 3.反射



  • 反射实例1

  • 反射实例2

  • 反射实例3







简介


反射(reflection)是什么?

在《精通C#》中是这么说的“反射就是一个运行库发现的过程”。



举例来说,通过反射,可以得到一个给定的.dll或.exe程序集所包含的所有类型的列表,这个列表包括给定类型定义的方法、字段、属性和事件。






引入


1.新建类库


右键解决方案->添加->新建项目->选择"类库"


在类库项目中添加几个自定义的类(在《C#入门经典》中发现新建类可以使用VS中自带的类图添加,但是我感觉不是很方便,但是不得不承认VS的查看类图,对阅读项目代码还是很有帮助的)


右键类库项目点击生成,在项目的bin\DeBug文件夹中生成相应的程序集文件(dll格式).


2. 类库的使用


如果某个项目要使用某个类库,则我们在项目中添加引用,引用类库项目,并添加引用的项目的命名空间。这样就可以使用类库中定义的类了。


3.反射


对于程序集文件(dll和exe文件),他们是二进制文件,不能直接打开,但是我们想要查看里面的具体内容,我们该怎么办。


使用VS中的“对象浏览器”,直接右击引用文件,我们可以选择在对象浏览器中查看,就可以看到类库文件(dll文件)中的定义的类。


还有一种方法那就是使用VS自带的反编译工具ildasm.exe(C:\Program Files (x86)\Microsoft SDKs\Windows\v10.0A\bin\NETFX 4.6.1 Tools\x64\ildasm.exe)


但是在代码中怎么查看呢,这就要用到反射。

这就是动态加载程序集





反射实例1


在这里,我们把ClassLibrary1类库文件(dll文件)复制到项目的bin/Debug文件中


ClassLibrary1类库有三个类具体如下
C#-反射reflection


代码如下:


namespace _01程序集的引用
{
class Program
{
static void Main(string[] args)
{
#region 加载程序集
//获取基目录(也就是bin\deBug的绝对路径)
string deBuyPath = AppDomain.CurrentDomain.BaseDirectory;

//获取DeBug中的dll文件的绝对路径(通过类库项目生成的,我自己复制到那里的)
//using System.IO;
string dllPath = Path.Combine(deBuyPath, "ClassLibrary1.dll");

//加载程序集文件(using System.Reflection;)
Assembly ass = Assembly.LoadFile(dllPath);
#endregion


Console.WriteLine("获取程序集中所有定义的类的类名,包括internal和public");
Type[] allTypes = ass.GetTypes();
foreach (Type item in allTypes)
{
Console.WriteLine($"程序集ClassLibrary1.dll中有类:{item.Name }");
}


//获取程序集中指定的类的类型
Type p = ass.GetType("ClassLibrary1.Person");
Console.WriteLine($"获取指定的类,类名{p.Name},类的命名空间{p.Namespace}");


//获取所有程序集dll文件中定义的公共类型的类型(公共类)
Type[] publicTypes = ass.GetExportedTypes();


Console.ReadKey();

}
}
}



运行结果:



-----------获取程序集中所有定义的类的类名,包括internal和public---------

程序集ClassLibrary1.dll中有类:Person

程序集ClassLibrary1.dll中有类:Student

程序集ClassLibrary1.dll中有类:Teacher

-----------获取程序集中指定的类的类型---------

获取指定的类,类名Person,类的命名空间ClassLibrary1

-----------获取程序集中公共类---------

程序集ClassLibrary1.dll中的公共类有:Person

程序集ClassLibrary1.dll中的公共类有:Student






反射实例2


namespace _02程序集的引用2
{
class Program
{
static void Main(string[] args)
{
//查询变量的类型

//法1:已经声明了一个变量
string str = "abcd";
Type t1 = str.GetType();
Console.WriteLine(t1);

//法2:直接使用变量类型查询
Type t2 = typeof(string);
Console.WriteLine(t2);

//法3:直接使用Type.GetType()静态方法
Type t3 = Type.GetType("System.String");
Console.WriteLine(t3);

//我们可以获得string的类型名,我们可以使用类型对象来探测string类型的内部结构
foreach (MemberInfo item in t1.GetMembers ())
{
Console.WriteLine($"当前类型的公共成员类型{item.MemberType},成员名{item.Name }");
}


Console.ReadKey();

}
}
}




反射实例3


反射实例1中我们知道了类库中的各个成员的的类型,那么我们怎么才能新建一个该类型的对象呢(这就是晚期加载

注意啊,上面我们只是获得了各个类的类型(类名),并没有真正的获得这个类名这个变量

所以我们无法使用类名这个变量去new一个对象


建立程序集中类的对象



//建立程序集中类的对象
object person = Activator.CreateInstance(p, 24, "志铭", "男");


#region 获取类型的属性
//获取该对象的属性列表
Console.WriteLine("--------获取该对象的属性列表---------");
PropertyInfo[] pros = person.GetType().GetProperties();
foreach (PropertyInfo item in pros)
{
Console.WriteLine(item.Name);
}

//获得指定名称的属性
PropertyInfo pro = p.GetProperty("Name");
//获得对象person的指定的属性的值
string name = (string)pro.GetValue(person, null);
Console.WriteLine(name);
#endregion


#region 获取类型的方法列表
Console.WriteLine("-------获取类型的方法列表--------------");
MethodInfo[] methods = person.GetType().GetMethods();
foreach (MethodInfo item in methods)
{
Console.WriteLine(item.Name);
}

//调用指定名称的方法
MethodInfo method = person.GetType().GetMethod("Say");
method.Invoke(person, null);
#endregion

//获取字段列表(注意你只能获取公共类型的字段)
FieldInfo[] fields = person.GetType().GetFields();
foreach (FieldInfo item in fields)
{
Console.WriteLine(item.Name);
}

Console.ReadKey();







推荐阅读
  • 一.介绍string和CString均是字符串模板类,string为标准模板类(STL)定义的字符串类,已经纳入C标准之中 ... [详细]
  • 针对上一期关于 Windows 8 的问题,我们正在积极解决。本文提供 IE6,7,8 三个版本的单文件版下载,适用于 Windows Vista/7 系统,支持 x86 和 x64 架构。欢迎大家下载并分享。 ... [详细]
  • 本文探讨了在C#服务中捕获控制台输出的有效方法,特别是在远程系统部署的应用场景下。文中不仅提供了基础的解决方案,还深入讨论了最佳实践,如使用日志库和事件日志等。 ... [详细]
  • 本文详细介绍了在Windows系统中安装PyCharm集成开发环境以及MySQL数据库的具体步骤,包括必要的环境配置和常见问题的解决方法。 ... [详细]
  • 动态链接技术:实现程序间代码共享
    本文介绍了动态链接的概念及其在程序开发中的重要性。通过动态链接,多个程序可以共享同一份代码,有效减少内存占用并提高系统效率。文章详细解释了动态链接与静态链接的区别,以及如何通过地址无关代码、PLT和GOT等机制实现代码共享。 ... [详细]
  • 通过使用反射创建对象,废话不多说直接上代码usingSystem.Reflection;namespaceFactory{publicclassDALFactor ... [详细]
  • 本文详细介绍了WebRTC提供的音频处理引擎,包括自动增益控制(AGC)、噪声抑制(ANS)、移动设备声学回声消除(AEC)及静音检测(VAD)等核心算法,并提供了完整的C语言实现代码。 ... [详细]
  • 在安装 CUDA Toolkit 时,系统会自动安装 NVIDIA 驱动。然而,这些默认的驱动可能不适合所有用户的硬件配置,因此有时需要手动安装特定版本的 NVIDIA 驱动。本文将详细介绍如何在 Ubuntu 14.04 系统上正确安装 NVIDIA 驱动和 CUDA Toolkit。 ... [详细]
  • Python安装指南:掌握自定义安装选项
    随着Python编程语言的迅速发展,越来越多的人开始关注并学习这一强大的工具。本文将详细介绍如何正确安装Python,包括选择合适的版本、自定义安装路径以及配置环境变量等关键步骤。 ... [详细]
  • 掌握数据库引擎存储过程与系统视图查询:DBA与BI开发者的必备技能
    本文介绍了如何利用数据库引擎存储过程及系统视图查询数据库结构和对象信息,为数据库管理员(DBA)和商业智能(BI)开发人员提供实用的基础知识。文章涵盖了一系列常用的SQL Server存储过程和系统视图,帮助读者快速获取数据库的相关信息。 ... [详细]
  • https:www.jianshu.comp2d376a82ba8c?utm_campaignmaleskine&utm_contentnote&utm_mediumseo_not ... [详细]
  • ODBC介绍:开放式数据库连接详解
    本文详细介绍了ODBC(开放式数据库连接),这是一种允许应用程序访问多种数据库系统的标准API。自1992年由微软与Simba合作推出以来,ODBC已成为跨平台数据访问的重要标准。 ... [详细]
  • 部署新的ASP.NET Web应用程序构建(主要涉及DLL文件更改)后,服务器上的CPU使用率每几秒就会飙升至100%,问题似乎源自lsass.exe进程。这一现象与应用程序部署之间是否存在直接关联? ... [详细]
  • 本文详细介绍了如何设置局域网,并确保网络中的所有计算机能够相互访问和共享安装的软件。包括物理连接检查、TCP/IP设置、网络协议配置等多个方面。 ... [详细]
  • 在Ubuntu上通过Wine安装Photoshop CS6的详细指南
    针对专业设计师和图像处理人员,寻找能够完全替代Adobe Photoshop的开源软件往往不尽如人意。本文提供了一种解决方案,即通过Wine在Linux系统上安装Photoshop CS6,以实现更稳定的操作体验。 ... [详细]
author-avatar
欢迎bm访问老年人空间
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有