规格模式是组合模式的一种扩展,在框架性开发中使用较多(项目级开发很少使用),这里做一个简单的介绍。由于是摘录,上下文章节可以参考我的博客,http://hi.baidu.com/cbf4life,或者下载PDF文件也一样。 发带格式、带图片的DOC文档太麻烦了,刚刚还出现了内容都整理好了,然后附件上传不上来,就在那转圈,我晕,只有重新发了!

这里假设了一个这样一个场景,有一堆的User对象,UserProvider提供查询服务。们来看组合规格书(CompositeSpecification),它是一个抽象类,实现了与或非的操作,如下所示。
public abstract class CompositeSpecification implements IUserSpecification {
//是否满足条件有实现类实现
public abstract boolean isSatisfiedBy(User user);
//and操作
public IUserSpecification and(IUserSpecification spec) {
return new AndSpecification(this,spec);
}
//not操作
public IUserSpecification not() {
return new NotSpecification(this);
}
//or操作
public IUserSpecification or(IUserSpecification spec) {
return new OrSpecification(this,spec);
}
}
候选对象是否满足条件是由isSatisfiedBy方法决定的,它代表的是一个判断逻辑,由各个实现类实现。三个与或非操作在抽象类中实现,它是通过直接new了一个子类,如此设计非常符合单一职责原则,每个子类都有一个独立的职责,要么完成与操作,要么完成或操作,要么完成非操作。我们先来看与操作规格书,如下所示。
public class AndSpecification extends CompositeSpecification {
//传递两个规格书进行and操作
private IUserSpecification left;
private IUserSpecification right;
public AndSpecification(IUserSpecification _left,IUserSpecification _right){
this.left = _left;
this.right = _right;
}
//进行and运算
@Override
public boolean isSatisfiedBy(User user) {
return left.isSatisfiedBy(user) && right.isSatisfiedBy(user);
}
}
通过构造函数传递过来两个需要操作的规格书,然后通过isSatisfiedBy方法返回两者and操作结果。或规格书和非规格书与此类似,分别如下所示。
public class OrSpecification extends CompositeSpecification {
//左右两个规格书
private IUserSpecification left;
private IUserSpecification right;
public OrSpecification(IUserSpecification _left,IUserSpecification _right){
this.left = _left;
this.right = _right;
}
//or运算
@Override
public boolean isSatisfiedBy(User user) {
return left.isSatisfiedBy(user) || right.isSatisfiedBy(user);
}
}
public class NotSpecification extends CompositeSpecification {
//传递一个规格书
private IUserSpecification spec;
public NotSpecification(IUserSpecification _spec){
this.spec = _spec;
}
//not操作
@Override
public boolean isSatisfiedBy(User user) {
return !spec.isSatisfiedBy(user);
}
}
该三个规格书都是不发生变化的,只要使用该框架,三个规格书都要实现的,而且代码基本上是雷同的,所以才有了父类依赖子类的设计,否则是严禁出现父类依赖子类的情况。大家再仔细看看这三个规格书和组合规格书,代码很简单,但也很巧妙,它跳出了我们面向对象设计的思维,不变部分使用一种固化方式实现。
名字相等、年龄大于基准年龄、Like格式等规格书都有少许改变,把实现接口变为继承基类,我们以名字相等规格书为例,如下所示。
public class UserByNameEqual extends CompositeSpecification {
//基准姓名
private String name;
//构造函数传递基准姓名
public UserByNameEqual(String _name){
this.name = _name;
}
//检验用户是否满足条件
public boolean isSatisfiedBy(User user) {
return user.getName().equals(name);
}
}
仅仅修改了黑体部分,其他没有任何改变。另外两个规格书修改相同,不再赘述。其他的User及UserProvider没有任何改动,不再赘述。
我们修改一下场景类,如下所示。
public class Client {
public static void main(String[] args) {
//首先初始化一批用户
ArrayList<User> userList = new ArrayList<User>();
userList.add(new User("苏国庆",23));
userList.add(new User("国庆牛",82));
userList.add(new User("张国庆三",10));
userList.add(new User("李四",10));
//定义一个用户查询类
IUserProvider userProvider = new UserProvider(userList);
//打印出名字包含国庆的人员
System.out.println("===名字包含国庆的人员===");
//定义一个规格
IUserSpecification spec = new UserByAgeThan(25);
IUserSpecification spec2 = new UserByNameLike("%国庆%");
for(User u:userProvider.findUser(spec.and(spec2))){
System.out.println(u);
}
}
}
在场景类中我们建立了两个规格书,一个是年龄大于25的用户,一个是名字中包含“国庆”两个字的用户,这两个规格书之间的关系是与关系,运行结果如下:
===名字包含国庆的人员===
用户名:国庆牛 年龄:82

- 大小: 10.6 KB
分享到:
相关推荐
规格模式(Specification Pattern),是由Eric Evans和Martin Fowler共同提出的一个设计模式,主要用于封装对象的搜索标准和条件逻辑。该模式的核心思想是分离候选对象的选择声明与对候选对象的匹配过程。 在探讨该...
6. `specification`:这个文件可能是Specification模式的基类或抽象类,定义了核心方法,如`and()`、`or()`,用于组合规格,以及`toPredicate()`方法,用于将Specification转换为可执行的查询。 在实际应用中,我们...
此外,规格模式(Specification Pattern)是一种行为模式,它允许以一种声明式的方式来表达业务规则,使得业务逻辑易于理解且易于组合。 在Java代码实现中,你可以找到每种模式的具体应用示例,这有助于你理解和...
NodeJS的规范模式 NodeJS的规范模式实现。 适用于任何种类的验证,可以简化,提高可重用性并使代码更清晰。 尽管主要用于以检查业务规则,但是组合规则的思想提供了很大的灵活性。 这是该模式JavaScript实现,包括...
LPDDR5(6400M)规格是JEDEC(固态技术协会)制定的一种低功耗双数据速率5代内存标准,旨在提高移动设备和嵌入式系统的内存性能,同时降低能耗。JESD209-5是该标准的具体版本,发布于2019年2月。LPDDR5的引入对现代...
PXE Specification Version 2.1 是这份文档的核心,详细定义了PXE的工作原理和规范。 PXE的运作流程大致分为以下几个步骤: 1. **初始化**:当计算机启动时,如果配置了PXE功能,BIOS会查找支持PXE的网络适配器,...
Invalid Pattern Specification(亲测可用).md
本文档深入探讨了设计模式的形式化,特别是通过Balanced Pattern Specification Language (BPSL)对设计模式进行结构和行为方面的正式描述。此外,它还关注于设计模式的组合,即如何将两个或更多的模式整合在一起以...
如您所料,将SQL / HQL代码直接放入Specification对象不是一个好习惯,因为它破坏了数据与基础结构的明确分离。 可以选择实现知道如何将每个规范及其组合转换为SQL / HQL查询的转换器(请参阅Spring的...
PMBUS Power System Management Protocol Specification Part I – General Requirements, Transport And Electrical Interface
* USGMII 接口支持全双工模式,而网络接口则支持半双工和全双工模式。 * 能够发送 Packet Channel Header,以支持可编程的信息交换 между PHY 和 MAC,例如从 PHY 到 MAC 的 PTP 时间戳,以提高加密的 PTP ...
总之,PCIe M.2 specification规格书是一本全面的技术文档,包含了设计和开发M.2接口设备所需的所有关键信息。无论是为新的笔记本电脑设计M.2 SSD插槽,还是为扩展卡开发新的功能,这个规格书都是不可或缺的参考资料...
USB-IF公布了最新的USB命名规范,原来的USB 3.0和USB 3.1将会不再被命名,所有的USB标准都将被叫做USB 3.2,当然考虑到兼容性,USB 3.0至USB 3.2分别被叫做USB 3.2 Gen 1、USB 3.2 Gen 2、USB 3.2 Gen 2x2。...
5.2.1 Specification模式 5.2.2 Composite模式 5.2.3 Layer Supertype模式 5.3 应用设计原则 5.3.1 依赖倒置原则和依赖注入模式 5.3.2 接口分离原则 5.3.3 里氏替换原则 5.4 小结 第6章 服务层 6.1 服务...
Specification模式的核心思想是将复杂的业务逻辑转换为一系列简单的、可复用的规格(Specification)对象。这些规格对象可以根据需要进行组合,形成更复杂的查询条件。在Laravel中,我们可以使用这一模式来处理数据...
### SSD9 —— 软件规范、测试与维护 #### 课程介绍 SSD9是一门关于软件工程的基础课程,旨在让学生深入了解软件工程的基本原则和实践方法,从而提高软件产品的质量并使得软件开发过程更加可预测且经济高效。本...
设备树规格书是官方文档,详细阐述了设备树的语法、结构以及使用方法。下面我们将深入探讨设备树的相关知识点。 1. **设备树的基本概念** 设备树是一种数据结构,由一系列节点和属性组成,用于描述硬件平台的组成...
文章指出,尽管模式匹配是现代函数式编程语言的重要特性,但它与面向对象语言的中心目标——数据抽象和可扩展性——存在冲突。模式匹配允许根据数据的结构来执行不同的操作,这在处理代数数据类型(如树、列表等)时...