文档章节

动态加载dll,扩展系统功能

白志华
 白志华
发布于 2015/10/18 10:54
字数 905
阅读 6
收藏 0

动态加载dll,主要是为了扩展功能,增强灵活性而实现的。主要通过xml配置,来获取所有要动态加载的dll,然后通过反射机制来调用dll中的类及其方法。


研究了一天,小有所得,写了一个简单的动态加载dll的通用模块,拿出来与大家分享一下:


using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;

namespace DynamicLoadDLL
{
    /// <summary>
    /// 动态加载dll
    /// </summary>
    public class LoadDLL
    {
        private Assembly ass = null;

        /// <summary>
        /// 加载dll
        /// </summary>
        /// <param name="dllPath">dll文件路径</param>
        public LoadDLL(string dllPath)
        {
            this.ass = Assembly.LoadFrom(dllPath);                     //利用dll的路径加载(fullname)
        }

        /// <summary>
        /// 返回反射的dll
        /// </summary>
        /// <returns></returns>
        public Assembly GetAssembly()
        {
            return this.ass;
        }

        /// <summary>
        /// 获取所有类名
        /// </summary>
        /// <returns></returns>
        public Type[] GetClass()
        {
            return ass.GetTypes();
        }

        /// <summary>
        /// 获取程序集下的所有文件名
        /// </summary>
        /// <returns></returns>
        public Module[] GetModules()
        {
            return ass.GetModules();            
        }

        /// <summary>
        /// 获取程序集清单文件表中的文件
        /// </summary>
        /// <returns></returns>
        public FileStream[] GetFiles()
        {
            return ass.GetFiles();
        }

    }
}

这个是加载dll的,然后返回一个Assembly类型的一个反射值,如果该dll中有多个命名空间和类的话,就只用一个 Assembly类型的一个反射值即可以完成调用,否则每次生成一个类,都需要反射一次。IO操作相对而言是比较耗费CPU,影响效率的。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;

namespace DynamicLoadDLL
{
    /// <summary>
    /// 加载类
    /// </summary>
    public class LoadClass
    {
        private static LoadClass dlc = null;
        private Type type;
        private object obj = null;                                         //实例

        /// <summary>
        /// 加载dll
        /// </summary>
        /// <param name="ass">dll引用</param>
        /// <param name="nameSpace">类的命名空间</param>
        /// <param name="classPath">类名称</param>
        private LoadClass(Assembly ass, string nameSpace, string classPath)
        {
            //加载dll后,需要使用dll中某类.
            type = ass.GetType(nameSpace + "." + classPath);                                //利用类型的命名空间和名称获得类型

            //需要实例化类型,才可以使用,参数可以人为的指定,也可以无参数,静态实例可以省略
            obj = Activator.CreateInstance(type);                         //利用指定的参数实例话类型

        }

        /// <summary>
        /// 加载dll
        /// </summary>
        /// <param name="ass">dll引用</param>
        /// <param name="nameSpace">类的命名空间</param>
        /// <param name="classPath">类名称</param>
        public static LoadClass GetInstance(Assembly ass, string nameSpace, string classPath)
        {
            if (dlc == null)
            {
                dlc = new LoadClass(ass, nameSpace, classPath);
            }
            return dlc;
        }

        /// <summary>
        /// 获取属性集
        /// </summary>
        /// <returns>返回属性值</returns>
        public PropertyInfo[] GetAttrs()
        {
            //调用类型中的某个属性:
            PropertyInfo[] prop = type.GetProperties();                //通过属性名称获得属性

            //返回属性集
            return prop;
        }

        public MethodInfo[] GetMethods()
        {
            //调用类型中的方法:
            MethodInfo[] method = type.GetMethods(BindingFlags.NonPublic);                //获得方法集

            //返回方法集
            return method;
        }


        /// <summary>
        /// 获取属性值
        /// </summary>
        /// <param name="attrName">属性名称</param>
        /// <returns>返回属性值</returns>
        public object GetAttrValue(string attrName)
        {
            //调用类型中的某个属性:
            PropertyInfo prop = type.GetProperty(attrName);                //通过属性名称获得属性

            //返回属性值
            return prop.GetValue(obj);
        }

        /// <summary>
        /// 设置属性值
        /// </summary>
        /// <param name="attrName">属性名称</param>
        /// <returns>返回属性值</returns>
        public void SetAttrValue(string attrName, string attrValue)
        {
            //调用类型中的某个属性:
            PropertyInfo prop = type.GetProperty(attrName);                //通过属性名称获得属性

            //返回属性值
            prop.SetValue(obj, attrValue);
        }

        /// <summary>
        /// 执行类方法
        /// </summary>
        /// <param name="methodName">方法名称</param>
        /// <param name="paras">参数</param>
        /// <param name="types">参数类型</param>
        /// <returns></returns>
        public object GetMethod(string methodName, object[] paras,Type[] types)
        {
            
            //调用类型中的某个方法:
            MethodInfo method = type.GetMethod(methodName,types);                //通过方法名称获得方法

            //执行方法
            return method.Invoke(obj, paras);
        }
    }
}

上面这个类根据dll反射值,命名空间和类名,反射出一个具体的类,还提供了属性和方法的调用方法。很方便。


这些是我在研究插件编程时,顺带研究的,不太深入,但希望对你能有所帮助。


版权声明:本文为博主原创文章,未经博主允许不得转载。

本文转载自:http://blog.csdn.net/xiaoxian8023/article/details/8334027

共有 人打赏支持
白志华
粉丝 30
博文 265
码字总数 57524
作品 0
长沙
程序员
私信 提问
dll的概念 dll导出变量 函数 类 (转)

1、 DLL的概念 DLL(Dynamic Linkable Library),动态链接库,可以向程序提供一些函数、变量或类。这些可以直接拿来使用。 静态链接库与动态链接库的区别: (1)静态链接库与动态链接库都是共...

长平狐
2012/10/08
675
0
qt实现-给SQLITE添加自定义函数

需要使用sqlite里的password对某个字段进行加密,由于使用的sqlite是由QT封装好的QSqlDatabase,没有发现加载扩展函数的方法,所以自己实现了一个。 在网上也没找到相应的参考,就自己查官方文...

quanwei9958
2014/12/21
0
0
LoadRunner使用动态链接库技术

什么是动态库? 动态库一般又叫动态链接库英文为DLL,是Dynamic Link Library 的缩写形式,DLL是一个包含可由多个程序同时使用的代码和数据的库,DLL不是可执行文件。动态链接提供了一种方法...

长平狐
2013/03/12
60
0
C语言dll文件的说明以及生成、使用方法

  最近在搞一些小项目,由于要涉及到跟其它语言进行交互,动态链接库变成了不二的选择。为此也查阅了很多资料,将动态链接库的相关知识在此做一个整理。   一、动态链接库概述   动态链...

雨淡云稠
2016/12/12
0
0
Linux-静态链接库和动态链接库

博文说明【前言】: 本文将通过个人口吻介绍Linux中静态链接库和动态链接库相关知识,在目前时间点【2017年6月14号】下,所掌握的技术水平有限,可能会存在不少知识理解不够深入或全面,望大...

1清风揽月1
2017/06/14
0
0

没有更多内容

加载失败,请刷新页面

加载更多

python中sort和sorted函数小结

L.sort(cmp=None, key=None, reverse=False) sorted(iterable, cmp=None, key=None, reverse=False) 这样看,sorted函数只比sort函数多一个iterable参数,其余没什么不同,iterable是一个迭代......

上官夏洛特
27分钟前
1
0
thinkphp 常用SQL执行语句总结

第一条:Db::tablera('vr_panomas')->where(['delete_time'=>0,'id'=>['in',$pids]])->field(['id'=>'id','post_thumb'=>'thumb','post_title'=>'title','post_tags'=>'tags','post_price'=>......

koothon
37分钟前
1
0
支付宝返回状态resultStatus意思

上一篇集成支付宝的时候,会有一些支付宝返回的resultStatus,具体意思是: 9000 订单支付成功 8000 正在处理中 4000 订单支付失败 6001 用户中途取消 6002 网络连接出错 还有memo,意思就是...

RainOrz
41分钟前
1
0
electron webview 页面加载事件顺序

1.did-start-loading 页面开始加载 2.load-commit 主页面文档加载 3.page-title-updated title 4.dom-ready 主页面 dom 加载完成 5.load-commit frame文档加载 6.did-frame-finish-load fram......

dubox
46分钟前
1
0
cron语法格式

Seconds Minutes Hours DayofMonth Month DayofWeek Year或 Seconds Minutes Hours DayofMonth Month DayofWeek...

JavaSon712
46分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部