在软件世界分层的思想无处不在

主要是为了提高软件系统的维护性,扩展性,复用性和解耦等

软件的三层构架是一种最基本的分层思想的体现

结构图大体如下:

如此一来,开发人员可以只关注其中一层,而无需关心下一层是如何实现的

但是最基本的三层构架在软件系统中很明显是不够用的

因为它带来优点的同时也带着许多缺点,比如耦合性高,经常出现修改某一层的代码另外一层也要随之大幅度整顿

而且当需求发生改变的时候,如:原先开发的时候使用mssql数据库,而现在又要求更换成mysql数据库

更换Dal层会导致Bll层也要重新设计

这时便可以使用工厂模式的三层

基本构架如下:

其实就是Bll和Dal层的代码分别实现他们接口层的接口

这体现了软件设计的针对接口编程的原则

为什么需要多出接口层实现呢

如,只要实现了IDAL层的接口

无论是mssql的Dal还是mysql的Dal层都可以随意的替换

通过一个工厂类来提供IDAL接口层的实体对象

Bll层中就只需要调用IDAL接口层中的方法就可以了而无需关心是谁实现的,怎么实现的

这时候如果要更换数据库所要修改的代码就大幅度减少了

只需要修改工厂类中相关的代码就可以,Bll层基本无需改动

但是这还是会修改代码

违反了软件设计原则中对扩展开发,对修改封闭的原则(开放-封闭原则)

我们可以利用反射技术来解决这个问题

我们可以再配置文件中配置好IDAL层中接口和Dal层中数据操作类所在的程序集名和所在的命名空间

在工厂类中根据配置文件中的信息利用反射动态创建Dal层的实体对象并转成IDAL中的接口

然后提供给Bll层使用

现在如果要更换数据库只需要更改配置文件中对应的程序集和命名空间信息就搞定,代码不需修改一行

(更绝的是,可以将配置信息放入数据库中,然后提供一个配置页面进行切换配置信息操作,这样一来连配置文件都不需要修改!)

上图中

因为各个实体类的CRUD方法都是差不多的,因此抽象出一个IBaseDal接口规定了CRUD的方法,并让IDAL层的所有接口都继承于这个基接口

同样对于Dal层的数据操作类,抽象出一个BaseDal基类,实现了IBaseDal中规定的CRUD基本方法,再次实现了代码复用

但是在很多的应用场景(如Web网站)

由于用户量大,可能导致很多问题,如数据不同步等多线程问题

可以采用线程内唯一的方案来对此问题进行改善

线程内唯一就是保证一个用户请求,访问的过程中只通过一个数据上下文进行操作,这样就不会出现因为缓存等情况而出现的数据混乱

上图在工厂模式的三层构架基础上添加了几个关键点:

1.在数据访问驱动之上设置了一个DbContextFactory工厂类,在此工厂类的内部通过CallContext方法从数据槽中取得唯一的数据访问驱动上下文

2.在IDAL接口层之上增设了DalContext层,该层是为了给Bll层一个调用IDAL接口的统一入口,但是其更重要的一个功能是通过一个公有的SaveChanges方法实现单元工作

3.和数据访问驱动层一样,在IDAL统一入口处设置了一个DalContextFactory工厂类来确保这个入口是线程内唯一的

那么什么是单元工作

比如在一个业务需求中

要对Users表进行添加

对Roles表进行删除

然后对Users和Roles的中间表进行修改

那么在此程序就会与数据库交互三次

但是如果是将三个操作线放入一个缓存中,等到最后一起提交到数据库

这样一来就减少了数据库的交互次数,提高了数据库的吞吐量

这就是单元工作模式

在EF中可以轻易的实现这个功能(在数据操作类中最后一步不要使用数据上下文的SaveChange保存操作,而是将其封装到DalContext中,使得Bll层可以在执行一系列的业务操作之后调用DalContext的SaveChanges方法进行统一的保存修改)

使用ADO.NET的话大致的思路就是将要执行的sql语句放入一个缓存队列中

通过另外一个工作进程通过轮询的方式(每隔一段时间,这个时间段间隔是非常小的)从缓存队列中取出sql语句一起提交到数据库

最后就是分布式的三层架构

我们可以通过WebService来比较简单的实现这一构架
在每层的WebService中通过该层的基本服务(简单三层,工厂三层或者线程内唯一+单元工作的三层等)
得到对应的接口
并通过这些接口的方法来接收和处理上一层发送的请求

.Net普通三层 到 工厂模式->线程内唯一+单元工作模式->WebService分布式三层的更多相关文章

  1. .Net普通三层->工厂模式->线程内唯一+单元工作模式->WebService分布式三层

    在软件世界分层的思想无处不在 主要是为了提高软件系统的维护性,扩展性,复用性和解耦等 软件的三层构架是一种最基本的分层思想的体现 结构图大体如下: 如此一来,开发人员可以只关注其中一层,而无需关心下一 ...

  2. MVC+Ef项目(3) 抽象数据库访问层的统一入口;EF上下文线程内唯一

    抽象一个数据库访问层的统一入口(类似于EF的上下文,拿到上下文,就可以拿到所有的表).实际这个入口就是一个类,类里面有所有的仓储对应的属性.这样,只要拿到这个类的实例,就可以点出所有的仓储,我们在 R ...

  3. EF 保证线程内唯一 上下文的创建

    1.ef添加完这个对象,就会自动返回这个对象数据库的内容,比如下面这个表是自增ID 最后打印出来的ID  就是自增的结果 2.lambda 中怎么select * var userInfoList = ...

  4. ASP.NET MVC+EF框架+EasyUI实现权限管理系列(8)-DbSession线程内唯一

    原文:ASP.NET MVC+EF框架+EasyUI实现权限管理系列(8)-DbSession线程内唯一 ASP.NET MVC+EF框架+EasyUI实现权限管系列 (开篇)   (1):框架搭建  ...

  5. ASP.net如何保证EF操作类线程内唯一

    说到线程内唯一,肯定会想到单例模式,但是如果多用户访问网站就会出现问题.ASP.net中有两种方法可以保证EF操作类线程内唯一(目前只会这两种,以后有好的方法再添加): 1.httpcontext(实 ...

  6. C# 如何保证对象线程内唯一:数据槽(CallContext)

    如果说,一个对象保证全局唯一,大家肯定会想到一个经典的设计模式:单例模式,如果要使用的对象必须是线程内唯一的呢? 数据槽:CallContext,ok看下msdn对callcontent的解释. Ca ...

  7. C# 如何保证对象线程内唯一:数据槽(CallContext)【转载】

    如果说,一个对象保证全局唯一,大家肯定会想到一个经典的设计模式:单例模式,如果要使用的对象必须是线程内唯一的呢? 数据槽:CallContext,ok看下msdn对callcontent的解释. Ca ...

  8. 单例模式和HttpContext线程内唯一

    单例模式 --> 多个用户会使用同一个EF,且这个EF一直不能释放,EF追踪的数据越来越多,服务器内存迟早爆炸(联想应用程序池,用户可能会用到被人用过的Application,里面的EF也是被用 ...

  9. EF上下文对象创建之线程内唯一

    在一次请求中,即一个线程内,若是用到EF数据上下文对象,就创建一个,那么会造成数据混乱,每次创建的对象执行相应的数据库操作,此同时,其他的EF对象内获得的数据可能已经是“过期”的了.即这个数据已经变动 ...

随机推荐

  1. PAT1001

    时间限制 400 ms 内存限制 65536 kB 代码长度限制 16000 B Calculate a + b and output the sum in standard format 计算a+b ...

  2. HDU 3487 Play with Chain | Splay

    Play with Chain Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) ...

  3. EM阅读资料

    1,从最大似然到EM算法浅解 2,(EM算法)The EM Algorithm 3,数据挖掘十大算法----EM算法(最大期望算法) (番外)最大后验估计(MAP)

  4. Nodejs开源项目里怎么样写测试、CI和代码测试覆盖率

    测试 目前主流的就bdd和tdd,自己查一下差异 推荐 mocha和tape 另外Jasmine也挺有名,angularjs用它,不过挺麻烦的,还有一个选择是qunit,最初是为jquery测试写的, ...

  5. angular 实现modal windows效果(即模态窗口,半透明的遮罩层),以及bootstrap(css,components,js)的初步学习

    废话不说,直接上代码.可直接看效果,对着分析..今天算是bootstrap 入门了,开心.. 突然居然很多事情就是那样,不要太多的畏惧,迈出第一步其实就成功了一半了. <html ng-app= ...

  6. expdp.sh and impdp.sh

    ####expdp.sh ###### ------------- --   UAT   -- ------------- @D:\dba\change\UAT\eais\env\env_eaisua ...

  7. ajax编程**

    ajax 编程 *step1获得 XmlHttpRequest 对象.该对象由浏览器提供,但是该类型并没有标准化.ie 和其它浏览器不同,其它浏览器都支持该类型,而 ie 不支持. function ...

  8. 需要注意的subList方法!和substring是不一样的!从源码解释他们的不同。

    很多时候我们截取字符串用的是substring方法,很自然用着,但是对于列表的截取时很多时候就用得很少,但是其实他们是很不一样的,具体哪里不一样呢? package main; import java ...

  9. 利用dokan作虚拟磁盘开发

    dokan是用户态的文件系统驱动,可以称之为fuse for windows.可以用来开发虚拟磁盘,即在“我的电脑”中虚拟出一个硬盘来,可以是硬盘,也可以是可移动磁盘或者网络硬盘. CreateFil ...

  10. 只有mdf 没有 日志 恢复数据库

    1.先建一个与你要恢复的数据库名称一样的数据库.2.停止sql server,把你的数据库替换这个数据库.3.重启sql server,把数据库设置为紧急状态.  sp_configure 'allo ...