前面三篇讲了MEF的基础和基本到导入导出方法,下面就是见证MEF真正魅力所在的时刻。若是没有看过前面的文章,请到个人博客首页查看。html
前面咱们都是在一个项目中写了一个类来测试的,但实际开发中,咱们每每要采用分层架构,就拿最简单的三层架构来讲吧,咱们一般把业务逻辑写在DLL中,如今就来写一个例子,看看如何在不编译整个项目的状况下,轻松的实现扩展。先透露一下,咱们只要添加一个DLL就能够了。编程
这里就以银行为例子吧,首先新建一个控制台项目,还叫MEFDemo吧,而后建一个类库写接口,而后再建一个类库实现接口。项目结构以下:架构
MEFDemo和BankOfChina都只引用接口项目,MEFDemo不须要引用BankOfChina。post
BankInterface的代码以下,作个简单实例,写几个方法测试一下:学习
using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace BankInterface { public interface ICard { //帐户金额 double Money { get; set; } //获取帐户信息 string GetCountInfo(); //存钱 void SaveMoney(double money); //取钱 void CheckOutMoney(double money); } }
这里添加一个中国银行卡,实现接口,引用命名空间什么的再也不重复说了,不懂看前面的文章,代码以下:测试
using System; using System.Collections.Generic; using System.Linq; using System.Text; using BankInterface; using System.ComponentModel.Composition; namespace BankOfChina { [Export(typeof(ICard))] public class ZHCard : ICard { public string GetCountInfo() { return "Bank Of China"; } public void SaveMoney(double money) { this.Money += money; } public void CheckOutMoney(double money) { this.Money -= money; } public double Money { get; set; } } }
而后编写主程序,代码以下:this
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Reflection; using System.ComponentModel.Composition; using System.ComponentModel.Composition.Hosting; using BankInterface; namespace MEFDemo { class Program { [ImportMany(typeof(ICard))] public IEnumerable<ICard> cards { get; set; } static void Main(string[] args) { Program pro = new Program(); pro.Compose();
foreach (var c in pro.cards)
{
Console.WriteLine(c.GetCountInfo());
}spa
Console.Read(); } private void Compose() { var catalog = new DirectoryCatalog("Cards"); var container = new CompositionContainer(catalog); container.ComposeParts(this); } } }
如今,咱们知道只有一种银行卡,及中国银行的,注意我标红的代码,这里是一个目录,及主程序所在目录的Cards文件夹,咱们把生成的BankOfChian.dll拷贝到这个文件夹下,而后运行才能够正确输出信息(毕竟咱们没有引用那个项目),如图:code
到了这里相信你们已经明白了,若是如今需求改变了,须要支持建行、农行等银行卡,怎么办呢?一般咱们要改项目,把整个项目都编译再从新发布。可是如今不须要这么作了,咱们只须要添加一个类库项目,把生成的dll拷贝到Cards目录下便可。htm
咱们在这个解决方案下继续添加一个类库项目,实现ICard接口,代码以下:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.ComponentModel.Composition; using BankInterface; namespace NongHang { [Export(typeof(ICard))] public class NHCard : ICard { public string GetCountInfo() { return "Nong Ye Yin Hang"; } public void SaveMoney(double money) { this.Money += money; } public void CheckOutMoney(double money) { this.Money -= money; } public double Money { get; set; } } }
点击右键编译,把生成的dll拷贝到Cards目录下面,运行看到以下结果:
再看看Cards目录中,如今你添加几个dll,就会显示多少条信息了。
MEF系列文章:
C#可扩展编程之MEF学习笔记(一):MEF简介及简单的Demo