`
axengine
  • 浏览: 142890 次
  • 性别: Icon_minigender_1
  • 来自: 重庆
社区版块
存档分类
最新评论

多接口+工厂模式=去耦架构

阅读更多
在这篇教程中,我们将会试图弄明白,如何使用多接口与工厂模式去生成一个真正的去耦合架构的框架(a truly decoupled architecture framework)。在例子中我们将会使用一个三级架构,并使用多接口与工厂模式去展示我们如何将一个三级架构转变成一个真正的去耦架构。 以前我曾经写过并录制了一些有关设计模式,UML,FPA,企业模块等等一些视频。你可以在http://www.questpond.com  看到它们。 你可以在 http://www.questpond.com/SampleDotNetInterviewQuestionBook.zip 下载到400本我关于.net FAQ的电子书。 所有人都偏爱三级架构。 ok。大家都知道三级架构是什么。我将会稍微讨论一下它,然后我们开始认真考虑一些有关三级架构的争议之处。基本上我们知道,三级架构中,UI代码 属于客户端部分,业务对象是只是一些有关业务验证的业务类。数据访问层处理所有有关的数据库操作。到这里为止,一切都相当完美。 如果我们分析一下这三个部分,就会注意到很重要的一点,其中的业务验证部分是相当反复无常(高度易变)的。业务规则的改变就相当于业务方式的改变。 第二易变的是客户端部分。人们倾向于多客户端支持,这依赖于用户接口。相对于业务对象来说,这并不是那么反复易变。即使用户想要改变它,也不会急于一时。而业务验证一旦变化则需要即刻的改变。 数据访问是最不常改变的部分。至少在我所有工程项目中,我依然遇到了一些需要经常移动数据库的项目。当一有需要的时候就会被移动,但这不会紧迫,同时它会被作为一个移植项目对待。 因此结论就是,业务部分是最容易频繁更改的,当它发生变化的时候,代码需要即刻进行修正。接下来是UI,最后才是数据库。 控制连锁变化 下面是一个叫做”clsInvoiceHeader”的业务类。你可以看到在代码部分,用户接口直接设定成业务对象。因此用户接口可以直接使用这个类。 clsInvoiceDetail objInvoiceDetail = new clsInvoiceDetail (); objInvoiceDetail.CustomerName = txtCustomerName.Text; objInvoiceDetail.CustomerAddress = txtCustomerAddress.Text; objInvoiceDetail.InvoiceComments = txtComments.Text; objInvoiceDetail.InvoiceDate=Convert.ToDateTime(txtInvoiceDate.Text); 另一方面,当业务对象连接数据访问层的时候,它会将值以普通的.NET数据类型发送出去。你会看到一个 DAL 部件‘InsertInvoiceDetails’如何发送普通的.NET数据类型。 public class clsInvoiceDetail { public void Insert(int _InvoiceReference) { clsInvoiceDB objInvoiceDB = new clsInvoiceDB(); objInvoiceDB.InsertInvoiceDetails(_Id, _InvoiceReference, _ProductId, _Qty); }} 因此,当业务对象发生变化的时候,会发生什么?它会把变化传导到所有的3个层。那意味着你需要重新编译整个工程。 接口与工厂模式的魅力 我们如何在所有的层次之间控制这种连锁反应呢?答案是通过接口与工厂模式。让我们先为‘clsInvoiceDetail’ 类创建一个接口。下面是接口代码。 public interface IInvoiceDetail { string InvoiceReferenceNumber { get; } string CustomerName { set; get; } string CustomerAddress { set; get; } string InvoiceComments { set; get; } DateTime InvoiceDate { set; get; }} 第二步,我们定义一个类用来创建‘clsInvoiceDetails’对象。下面是同样的代码。 public class FactoryFinance { public static IInvoiceDetail getInvoiceDetail() { return new clsInvoiceDetail(); } } 至此,客户只能通过作为代理的接口来引用以及使用工厂来创建具体的类‘ClsInvoiceDetail’。用这种方式,客户并不需要知道具体类 ‘ClsInvoiceDetail’的信息。工厂类的引进是为了避免在客户端引进新的关键字。如果我们在UI中有使用新关键字的客户端,并且UI直接与 具体类信息接触,这会导致严重的耦合。 IInvoiceDetails objInvoiceDetail = FactoryFinance.GetInvoiceDetails(); objInvoiceDetail.CustomerName [...]
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics