利用泛型减少重复,实现简易AOP

利用泛型减少重复,实现简易AOP

一、设计原则之DRY,不要重复自己

   在所有设计原则中,DRP(Don‘t Repeat Yourself)是最基础的原则之一。是由 Andy Hunt 和 Dave Thomas 在 The Pragmatic Programmer 中总结出来的,

成为软件开发和设计的最佳实践基础。开发者认识到,通过好的实践和适当的抽象可以减少重复,使程序的代码变得简洁。

重复是一种浪费。程序中的每一行代码都需要维护,重复就会导致出现bug的机会增多,也增加了系统的复杂度。对开发者而言,修改一个地方,而没有修改其他相同

逻辑的地方会让他们感到很难维护。单一职责要求:每个知识点必须有一个唯一的,明确的,权威的描述。

重复的过程需要自动化。DRP可以用在过程上,比如手工测试,慢,容易出错,而且难以重复,自动化测试就可以解决这些问题。凡是可以标准化,重复的过程都可以自动化。

重复的逻辑需要抽象。逻辑中的重复,比如拷贝的if-then swith-case 语句是很容易检查到的,很多设计模式就是来解决这种问题。如果一个对象的创建之前需要做很多事情,

可以用工程模式来封装,如果一个对象的行为有很多种变化,可以用策略模式来处理,而不是用大量的if else  语句。

DRP 是基础,比如开闭原则,单一职责,一次且仅一次的原则都是建立在DRP原则之上

二、泛型基础

泛型是C# 2.0 提出的特性,所谓泛型,即通过参数化类型实现在同一份代码上操作多种类型的数据,泛型编程是一种范式的转化,利用参数化类型,将类型抽象化,

从而实现代码的灵活复用,精简代码。泛型的好处:

a.减少了对对象进行装箱和拆箱所导致的性能成本,提高了效率。

b.赋予了代码更强的类型安全。

c.实现了更为灵活的代码复用。

例如: 安全性 装箱拆箱

var list = new  ArrayList();

list.Add(44); //装箱

list.Add("mystring");

list.Add(new  MyClass());

int i = (int)list[0]; //拆箱

list的就是不安全的,如果我们要对他继续类型转换,那么他就会出现异常。而且他add int类型,string类型的时候就要涉及装箱,你取出来的时候要涉及的拆箱

泛型格式:

泛型类      class MyClass<T>{}

泛型方法    T Function<T>()

泛型接口    interface MyInterfac <T> ,.NET类库里有很多泛型的接口 比如:IEnumerator<T>、IList<T>等

泛型委托    delegate void MyAction<T>(T obj);

.NET类库在System名称空间,下定义了三种比较常用的泛型委托
Predicate<T>委托:delegate
bool Predicate<T>(T obj);
Func<T>委托     :TResult Func<in T,
out TResult>(T arg);
Action<T>委托   :delegate void Action<in
T>(T obj);

在定义泛型时,可以对客户端代码在实例化类时用于类型参数的类型施加一些限制,这些限制称为约束,约束是使用where关键字实现的。..

下表列出了五种类型的约束:


T:struct


类型参数必须是值类型。 Nullable can be specified.">可以指定除 Nullable 以外的任何值类型。


T:类


类型参数必须是引用类型;这一点也适用于任何类、接口、委托或数组类型。


T:new()


类型参数必须具有无参数的公共构造函数。 new() constraint must be specified last.">当与其他约束一起使用时,new() 约束必须最后指定。


T:<基类名>


类型参数必须是指定的基类或派生自指定的基类。


T:<接口名称>


类型参数必须是指定的接口或实现指定的接口。 可以指定多个接口约束。 约束接口也可以是泛型的。

class EmployeeList<T> where T : Employee, IEmployee,
System.IComparable<T>,
new()

{

    // ...

}

这个是多类,接口,无参数的公共构造函数 各种进行了约束

默认值, 
我们可以用default关键字为  泛型 设置默认值

public T GetT()

{

    return default(T);

}

三、EAP里面的重复代码

在Imp
接口实现层,有很多重复的代码,最常见的重复是日志和异常的处理代码,还有返回值的处理,例如:

  
这里真正的业务代码只有1句   result.Value =
this.BillBfl.GetImportBillSubSys();

这里真正的业务代码只有2句

TNBillLayout layout =
TNBillLayout.FromJson(jsonparam);

this.BillBfl.SaveBillLayout(layout);

这种代码在Imp层有很多,随处可见。 其他都是类似的,拷贝的,容易出错。

四、利用泛型改造后的代码

利用泛型方法和泛型委托,可以将上面的日志和异常处理提炼出来。例如:有返回值的泛型方法

无返回值的泛型方法

EAP中封装了如下的泛型方法,包含多至5个参数的又返回值和无返回值的泛型方法
 

专门针对IMP层代码的泛型方法

  

最多6个参数的泛型方法

改造后的代码:

  总结:
利用泛型方法,可以实现日志,异常,性能计数的拦截,实现简易的AOP,同时减少重复,使代码变得简洁。

时间: 2024-11-08 14:29:57

利用泛型减少重复,实现简易AOP的相关文章

用泛型减少重复代码,使代码更合理、更优雅

有这样一个场景,需要对接接口,以获取取得数据. 例如获取订单列表 接口请求参数(json格式): 1 { 2 //公共头部 3 "head":{ 4 "method":"getOrders", //接口方法 5 "sign":"xxxx" //签名 6 }, 7 //私有主体 8 "body":{ 9 "userId":"1", //用户ID 10

如何有效的减少重复的代码

重复的代码一直都是可维护性的大敌,重构的重要任务之一也就是要去除掉重复的代码,有效的减少重复代码,可以大大提高软件的扩展性. 在Android开发中,很容易产生重复的代码.因为Android是组件,模板式开发,每个页面都是独立用Activity或Fragment实现,布局文件都是用XML方式去写,所以很容易造成代码的重复,虽然二个页长的差不多,但毕竟是二个Activity,于是就拷一份出来,改吧改吧就成了. 那么我们如何做才能去掉重复的代码呢? 点击阅读全文

从头认识java-13.5 利用泛型构建复杂模型

这一章节我们来展示一下如何利用泛型构建复杂模型? 1.元组列表 我们之前已经说过元组是一个复杂的模型,能够返回多对象. package com.ray.ch11; import java.util.ArrayList; public class Test { public ArrayList<Tuple<A, B, C>> test() { ArrayList<Tuple<A, B, C>> list = new ArrayList<Tuple<

利用泛型抽取Dao层,加事务注解问题(java.lang.Class cannot be cast to java.lang.reflect.ParameterizedType)

想利用泛型抽取BaseDao层,简化操作时出现问题: @Transactional这个注解是可以继承的,于是就想写在抽取的BaseDao层上,让实现的类可以不用写@Transactional,就可开启事务. 问题描述: 由于偷懒,没给BaseDao抽接口,代码如下: package com.liang.ssh2.base; import java.lang.reflect.ParameterizedType; import java.util.Collections; import java.u

无限层级且乱序的树形结构数据的整理,利用HashMap减少遍历次数

我们在展示一个机构树的时候,常常会遇到这样的一个问题,查询数据的时候,是从下往上查的,但展示数据的时候,又要从下往上展示. 这时候就要把查询到的数据进行整理从而得到我们想要的结构. 举个例子. ID PARENT_ID SOME_ATTRIBUTE_ID 2001 0   6292 6120 57010 6120 6115   6121 6115   6156 6121 56874 6115 2001   这是根据需求查询出的sql数据,但是它是无序的,所以很让人头疼,不知如何去处理,示意图是这

.Net利用泛型封装EF CodeFirst 数据库初始值设定项

在使用 EF的code fist 方法我们可能会用到这三个类型对象DropCreateDatabaseAlways(总是删除创建对象) DropCreateDatabaseIfModelChanges(如果对象盖面删除创建对象) CreateDatabaseIfNotExists(如果对象不存在删除创建对象) 今天就利用泛型和工厂模式,将这三个对象封装以下,首先对三个对象类型分别创建子类,便于后期扩展. public class MyDropCreateDatabaseAlways<T> :

C#当中利用Attribute实现简易AOP

首先看一段简单的代码: public partial class Form1 : Form { public Form1() { InitializeComponent(); } //来自UI层的调用 private void button1_Click(object sender, EventArgs e) { BusinessHandler handler = new BusinessHandler(); handler.DoSomething(); } } //业务层的类和方法 publi

减少重复工作,通过泛型、反射写一个通用的Ado.net操作数据库的简单orm底层

创建一个基类BaseEntity: public class BaseEntity { [PrimaryKey] public int Id { get; set; } public DateTime CreateTime { get; set; } public Status Status { get; set; } public string Remark { get; set; } } /// <summary> /// 自增主键标识 /// </summary> publi

不用Unity库,利用.NET动态代理自己实现AOP

AOP意为面向切面的程序设计,主要表现为对不同的代码逻辑进行隔离,从而降低不同业务逻辑之间的耦合性,AOP又理解为“横切”,可以在不改变原有实现的情况下,对代码进行拦截和扩展,如果原有设计像一个瓶子,AOP就相当于一个贴纸,是贴在瓶子外面的,而不是打开瓶盖从瓶口把实现放进瓶子里. .NET中实现AOP的第三方库有很多,这里不再阐述了,在这里我们主要用到了.NET中的动态代理技术,为了让大家更深入地理解,这里借用一下上一篇文章(不用Unity库,自己实现.NET轻量级依赖注入)中的例子,在上一篇文