本文版权归博客园和作者吴双本人共同所有。欢迎转载,转载和爬虫请注明原文地址  http://www.cnblogs.com/tdws/p/5861842.html

昨天晚上,有个朋友说学了好久,依然没搞懂多态,让我简单讲解一下。我觉得多态在面向多想的三大特性当中,算是最简单的,最难的是看似容易的封装。在编写面向对象代码时,如何让代码可读性更强,除了变量和方法命名标准外,要做的到一个方法只做一件事情,这样的思想是《代码整洁之道》一书中主要推崇的思想,其实有经验的各位都希望自己看到的代码是简短,可维护,可读性强的,相信大家也都“有幸”遇到过几百上千行的代码,更过分的是有个朋友曾经维护一个上万行的Action,夸张的说,调试并走通逻辑,一次要三天,有的人说这是业务逻辑不断增加所导致,但我认为,在这种情况下,更应该尽量做到一个方法做一件事情。我也不多吐槽了,关于代码整洁,我在大三的时候,就"吐槽"过http://www.cnblogs.com/tdws/p/4674489.html。

封装也不是今天的主题,今天我们要说的是多态,在朋友问我的时候,我给他举了下面这个简短的例子。

总体概括这个例子来讲就是在基本的三层架构当中,DAL层建两个类AdminDal,UserDal。两个类中,都有增加对象和删除对象地方法,那这个时候,我们应该给两个类抽象出一个父类BaseDal<T>,父类中是他们的公共方法,并且父类需要一个泛型T,这样父类的方法,才能明白你所要添加或者删除的object到底是什么类型的。请看如下代码。虽然两个类的公共方法在父类当中,但是他们自身特有的方法,还是要写在自己的Dal层当中。

1   public class UserDal: BaseDal<UserEntity>
2   {
3
4   }

1   public class AdminDal: BaseDal<AdminEntity>
2     {
3         public void Manage()
4         {
5             Console.WriteLine("管理员管理网站");
6         }
7     }

 1 public class BaseDal<T>
 2     {
 3         public void AddObj(T obj)
 4         {
 5             Console.WriteLine("添加对象成功,对象属于"+obj.GetType().ToString());
 6         }
 7
 8         public void DeleteObj(T obj)
 9         {
10             Console.WriteLine("删除对象成功,对象属于"+obj.GetType().ToString());
11         }
12
13     }

下面给出逻辑层代码,如果说普通的开发过程当中,你的代码也许是这样的。

 1  public class UserBll
 2     {
 3         UserDal dal = new UserDal();
 4
 5         public void Add(UserEntity obj)
 6         {
 7             dal.AddObj(obj);
 8         }
 9
10         public void Delete(UserEntity obj)
11         {
12             dal.DeleteObj(obj);
13         }
14      }

    public class AdminBll     {AdminDal dal = new AdminDal();public void Add(AdminEntity admin){dal.AddObj(admin);}public void Delete(AdminEntity admin){dal.DeleteObj(admin);}public void Manage(){dal.Manage();}}

也就是在各自的逻辑层当中,调用dal层。这个时候你又看到依然有这么多重复的代码,是不是应该再次封装成一个BaseBll<T>呢。答案是肯定的,但是问题又来了,在封装父类的过程中,你会发现,这个dal的对象怎么封装呢?这就是用到多态的关键点。下面看一下BaseBll.cs的代码。

 public abstract class BaseBll<T> where T:class, new(){public BaseDal<T> currentDal;public BaseBll(){SetCurrentDal();}public abstract void SetCurrentDal();public void BaseAdd(T obj){currentDal.AddObj(obj);}public void BaseDelete(T obj){currentDal.DeleteObj(obj);}}

我给了一个抽象的基类,并且给出抽象的SetCurrentDal的抽象方法定义。该方法用于设置当前类的currentDal到底是adminDal还是userDal。我们在构造函数中调用SetCurrentDal这个抽象方法,为什么在构造函数中调用的原因是,当实例化子类对象时,一定是首先进入其父类的构造函数。当子类AdminBll和UserBll继承BaseBll<T>的时候,必须重写抽象方法,并且为BaseDal<T> currentDal对象设置实际的值。我先给出子类的代码

 1 public class AdminBll : BaseBll<AdminEntity>
 2     {
 3         AdminDal dal = new AdminDal();
 4         public AdminBll()
 5         {
 6
 7         }
 8         public void Manage()
 9         {
10             new AdminDal().Manage();
11         }
12
13         public override void SetCurrentDal()
14         {
15             currentDal = new AdminDal();
16         }
17     }

1 public class UserBll : BaseBll<UserEntity>
2     {
3         public override void SetCurrentDal()
4         {
5             base.currentDal = new UserDal();
6         }
7     }

当实例化子类的对象时,过程为:子类构造函数(不进入)—进入父类构造函数—父类构造内部调用子类重写的SetCurrentDal(当前多态的currentDal到底是谁的实例)—父类构造执行完毕(设置currentDal完成)—子类构造函数。这就是抽象方法实现的多态。

下面在UI层调用一下,看看结果:

 1     class Program
 2     {
 3         static void Main(string[] args)
 4         {
 5             AdminBll adminBll = new AdminBll();
 6             AdminEntity admin = new AdminEntity() {AdminName="吴双",AdminPwd="123" };
 7             adminBll.Manage();
 8             adminBll.BaseAdd(admin);
 9             Console.ReadKey();
10         }
11     }

输出结果:

在开发的过程中,也许你会有很多实体类,每个实体类都有各自的增删改查等其他共有方法,基于这样的情况,我们就需要手段来将其封装。为什么在逻辑层使用了多态,原因就是我们封装父类的时候,不确定当前的currentDal到底是adminDal还是userDal还是xxxDal。为了封装出基类,这个多态的对象就必不可少了。

当然在实际当中,如果你是写原生sql,这样封装的确不容易,各种拼接sql。但如果说你用ORM框架,EF,Dapper之类的,这个方法真的是必不可少的,你可能再加上接口层,加上工作单元,创建对象非new,使用抽象工厂,依赖注入等。无论怎样,这一层的多态一定能用到,只是创建对象稍作修改。

下一阶段也打算进行后台架构搭建分享,MVC WebApi+EF/Dapper+工作单元+抽象工厂/依赖注入Autofac+AutoMapper+日志组件等。

我也曾多次在项目中搭建此类框架,在缓存提高性能,处理高并发,应用服务器集群,缓存集群,队列集群等方面,本次也会加入到分享当中。

如果今天的点滴分享,对您有点滴帮助,请点赞支持,也为自己的进步点赞。

点击下方关注,我们共同进步。

C#多态“说来也说”——逻辑层BLL中的多态使用相关推荐

  1. 网上购物系统(Task100)——业务逻辑层BLL(面向接口的编程模式)

    源代码:13033480群共享 [操作步骤] 一.新建类库IDAL,设置属性,添加引用→项目→Model 二.添加类ICategory.cs和IItem.cs 1.ICategory.cs using ...

  2. 桥接模式的应用之三层架构中的业务逻辑层(BLL)与数据访问层(DAL)的解耦

    各层的作用 ①用户界面层:只负责显示和采集用户操作. ②业务逻辑层:负责UI和DAL层之间的数据交换,是系统架构中体现核心价值的部分.它关注点主要集中在业务规则的制定.业务流程的实现和业务需求的有关系 ...

  3. 业务逻辑层service中常用注解

    注解的定义只是说它能作用在哪儿,它能提供哪些参数,具体什么时候用到,那是spring里的东西.注解只是一个标签,告诉spring ioc这个类是个什么东西 业务逻辑层类注解 @Service 打印日志 ...

  4. java多态app_【Java基础】Java中的多态

    什么是多态 多态是一个对象的多种实现,是建立在继承的基础上的,即对象"人",有老师和学生不同的实现,其实总结起来就是允许将子类类型的指针赋值给父类类型的指针. 多态的发生条件 多态 ...

  5. android ui层 交互层 业务逻辑层 服务层,表现层(UI)、业务逻辑层(BLL)、数据访问层(DAL)...

    三层架构(3-tier application) 通常意义上的三层架构就是将整个业务应用划分为:表现层(UI).业务逻辑层(BLL).数据访问层(DAL).区分层次的目的即为了"高内聚,低耦 ...

  6. petshop详解之五:PetShop之业务逻辑层设计

    五 PetShop之业务逻辑层设计业务逻辑层(Business Logic Layer)无疑是系统架构中体现核心价值的部分.它的关注点主要集中在业务规则的制定.业务流程的实现等与业务需求有关的系统设计 ...

  7. petshop4.0 详解之五(PetShop之业务逻辑层设计)[转]

    业务逻辑层(Business Logic Layer)无疑是系统架构中体现核心价值的部分.它的关注点主要集中在业务规则的制定.业务流程的实现等与业务需求有关的系统设计,也即是说它是与系统所应对的领域( ...

  8. petshop4.0 详解之五(PetShop之业务逻辑层设计)

    五 PetShop之业务逻辑层设计 业务逻辑层(Business Logic Layer)无疑是系统架构中体现核心价值的部分.它的关注点主要集中在业务规则的制定.业务流程的实现等与业务需求有关的系统设 ...

  9. PetShop之业务逻辑层设计

    <解剖PetShop>系列之五 五 PetShop之业务逻辑层设计 业务逻辑层(Business Logic Layer)无疑是系统架构中体现核心价值的部分.它的关注点主要集中在业务规则的 ...

  10. [wayfarer]PetShop之业务逻辑层设计

    原文地址: http://www.cnblogs.com/wayfarer/archive/2006/11/05/550723.html <解剖PetShop>系列之五 五 PetShop ...

最新文章

  1. 云原生架构下日志服务数据预处理
  2. React基础学习(第二天)
  3. C# 8.x 先睹为快
  4. L3-020 至多删三个字符 [DP]
  5. 为什么两层3*3卷积核效果比1层5*5卷积核效果要好?
  6. C#利用反射将实体类ListT转化为Datatable
  7. 【算法】剑指 Offer 47. 礼物的最大价值
  8. java.util.stream.LongStream
  9. 创建My SQL 数据库
  10. 操作系统原理学习总结
  11. 数据结构试卷及答案(二)
  12. layui修改头像功能
  13. 真人qq秀代码_关于QQ我的记忆
  14. Mach-O文件, 架构包framework的合并和拆分
  15. 从Mac的GUID分区谈起
  16. 利用selenium在虎牙直播发送弹幕
  17. 古籍、中国通史、诗经、辞、、四书五经、诸子百家、四大名著、唐诗、宋词、明清小说、四库全书
  18. 中国大学MOOC C语言程序设计(大连理工大学) 课后编程题 第十二周题解(个人向仅供参考)
  19. Matlab/Simulink代码生成到dsp系列(一)基础配置
  20. 机器学习中样本的样本量的估计(VC维)

热门文章

  1. C语言 文件操作5--文件的常用函数
  2. MMU页表的内存消耗
  3. 一个简单的Python调度器
  4. Oracle中UNION和ORDER BY共用方法
  5. Docker基础-容器操作
  6. wpf silverlight的Behavior
  7. 全球四大互联网公司最大的敌人是谁
  8. 省会城市房价地图,这9座新星城市正在悄然崛起
  9. 入门 ggplot2 的图形语法
  10. R语言数据清洗实战——高效list解析方案