设计模式(Design pattern)代表了最佳的实践,通常被有经验的面向对象的软件开发人员所采用。设计模式是软件开发人员在软件开发过程中面临的一般问题的解决方案。这些解决方案是众多软件开发人员经过相当长的一段时间的试验和错误总结出来的。
设计模式是一套被反复使用的、多数人知晓的、经过分类编目的、代码设计经验的总结。使用设计模式是为了重用代码、让代码更容易被他人理解、保证代码可靠性。 毫无疑问,设计模式于己于他人于系统都是多赢的,设计模式使代码编制真正工程化,设计模式是软件工程的基石,如同大厦的一块块砖石一样。项目中合理地运用设计模式可以完美地解决很多问题,每种模式在现实中都有相应的原理来与之对应,每种模式都描述了一个在我们周围不断重复发生的问题,以及该问题的核心解决方案,这也是设计模式能被广泛应用的原因。
模式定义: 一个类只有一个实例,且该类能自行创建这个实例,并提供一个访问它的全局访问点。
单例模式有 3 个特点:
模式优点:
模式缺点:
应用场景:
代码实现:
Singleton 模式通常有两种实现形式。
第 1 种:懒汉式单例
该模式的特点是类加载时没有生成单例,只有当第一次调用 getlnstance 方法时才去创建这个单例。代码如下:
public class LazySingleton {
// volatile 关键字保证了:1. instance 实例对所有线程都是可见的; 2. 禁止了 instance 操作指令冲排序。
private static volatile LazySingleton instance = null;
// private 避免类在外部被实例化
private LazySingleton() {}
public static synchronized LazySingleton getInstance() {
// 第一次校验,防止不必要的同步
if(instance == null) {
// synchronized 关键字加锁,保证每次只有一个线程执行对象初始化操作
synchronized (LazySingleton.class) {
// 第二次校验,进行判空,如果为空则执行初始化
if(instance == null) {
instance = new LazySingleton();
}
}
}
return instance;
}
}
> 注意:
如果编写的是多线程程序,则不要删除上例代码中的关键字 volatile 和 synchronized,否则将存在线程非安全的问题。如果不删除这两个关键字就能保证线程安全,但是每次访问时都要同步,会影响性能,且消耗更多的资源,这是懒汉式单例的缺点。
第 2 种:饿汉式单例
该模式的特点是类一旦加载就创建一个单例,保证在调用 getInstance 方法之前单例已经存在了。代码如下:
public class HungrySingleton {
private static final HungrySingleton instance = new HungrySingleton();
private HungrySingleton() {}
public static HungrySingleton getInstance() {
return instance;
}
}
> 饿汉式单例在类创建的同时就已经创建好一个静态的对象供系统使用,以后不再改变,所以是线程安全的,可以直接用于多线程而不会出现问题。
模式定义: 将一个复杂对象的构造与它的表示分离,使同样的构建过程可以创建不同的表示,这样的设计模式被称为建造者模式。它是将一个复杂的对象分解为多个简单的对象,然后一步一步构建而成。它将变与不变相分离,即产品的组成部分是不变的,但每一部分是可以灵活选择的。
模式优点:
模式缺点:
应用场景:
代码实现:
(1) 产品角色:包含多个组成部件的复杂对象。
class Product {
private String partA;
private String partB;
private String partC;
public void setPartA(String partA) {
this.partA=partA;
}
public void setPartB(String partB) {
this.partB=partB;
}
public void setPartC(String partC) {
this.partC=partC;
}
public void show() {
// 显示产品的特性
}
}
(2) 抽象建造者:包含创建产品各个子部件的抽象方法。
abstract class Builder {
// 创建产品对象
protected Product product=new Product();
public abstract void buildPartA();
public abstract void buildPartB();
public abstract void buildPartC();
// 返回产品对象
public Product getResult() {
return product;
}
}
(3) 具体建造者:实现了抽象建造者接口。
public class ConcreteBuilder extends Builder {
public void buildPartA() {
product.setPartA("建造 PartA");
}
public void buildPartB() {
product.setPartA("建造 PartB");
}
public void buildPartC() {
product.setPartA("建造 PartC");
}
}
(4) 指挥者:调用建造者中的方法完成复杂对象的创建。
class Director {
private Builder builder;
public Director(Builder builder) {
this.builder=builder;
}
// 产品构建与组装方法
public Product construct() {
builder.buildPartA();
builder.buildPartB();
builder.buildPartC();
return builder.getResult();
}
}
(5) 客户类。
public class Client {
public static void main(String[] args) {
Builder builder=new ConcreteBuilder();
Director director=new Director(builder);
Product product=director.construct();
product.show();
}
}
1.3 原型模
模式定义: 用一个已经创建的实例作为原型,通过复制该原型对象来创建一个和原型相同或相似的新对象。在这里,原型实例指定了要创建的对象的种类。用这种方式创建对象非常高效,根本无须知道对象创建的细节。
模式优点:
模式缺点:
应用场景:
代码实现:
原型模式的克隆分为浅克隆和深克隆。
Java 中的 Object 类提供了浅克隆的 clone() 方法,具体原型类只要实现 Cloneable 接口就可实现对象的浅克隆,这里的 Cloneable 接口就是抽象原型类。其代码如下:
// 具体原型类
class Realizetype implements Cloneable {
Realizetype() {
System.out.println("具体原型创建成功!");
}
public Object clone() throws CloneNotSupportedException {
System.out.println("具体原型复制成功!");
return (Realizetype)super.clone();
}
}
// 原型模式的测试类
public class PrototypeTest {
public static void main(String[] args)throws CloneNotSupportedException {
Realizetype obj1=new Realizetype();
Realizetype obj2=(Realizetype)obj1.clone();
System.out.println("obj1==obj2?"+(obj1==obj2));
}
}
模式定义: 简单来说,简单工厂模式有一个具体的工厂类,可以生成多个不同的产品。
模式优点:
模式缺点:
应用场景:
代码实现:
public class Client {
public static void main(String[] args) {
}
// 抽象产品
public interface Product {
void show();
}
// 具体产品:ProductA
static class ConcreteProduct1 implements Product {
public void show() {
System.out.println("具体产品1显示...");
}
}
// 具体产品:ProductB
static class ConcreteProduct2 implements Product {
public void show() {
System.out.println("具体产品2显示...");
}
}
final class Const {
static final int PRODUCT_A = 0;
static final int PRODUCT_B = 1;
static final int PRODUCT_C = 2;
}
static class SimpleFactory {
public static Product makeProduct(int kind) {
switch (kind) {
case Const.PRODUCT_A:
return new ConcreteProduct1();
case Const.PRODUCT_B:
return new ConcreteProduct2();
}
return null;
}
}
}
模式定义: 定义一个创建对象的接口,让其子类自己决定实例化哪一个工厂类,工厂模式使其创建过程延迟到子类进行。
模式优点:
模式缺点:
应用场景:
代码实现:
package FactoryMethod;
public class AbstractFactoryTest {
public static void main(String[] args) {
try {
Product a;
AbstractFactory af;
af = (AbstractFactory) ReadXML1.getObject();
a = af.newProduct();
a.show();
} catch (Exception e) {
System.out.println(e.getMessage());
}
}
}
// 抽象产品:提供了产品的接口
interface Product {
public void show();
}
// 具体产品1:实现抽象产品中的抽象方法
class ConcreteProduct1 implements Product {
public void show() {
System.out.println("具体产品1显示...");
}
}
// 具体产品2:实现抽象产品中的抽象方法
class ConcreteProduct2 implements Product {
public void show() {
System.out.println("具体产品2显示...");
}
}
// 抽象工厂:提供了厂品的生成方法
interface AbstractFactory {
public Product newProduct();
}
// 具体工厂1:实现了厂品的生成方法
class ConcreteFactory1 implements AbstractFactory {
public Product newProduct() {
System.out.println("具体工厂1生成-->具体产品1...");
return new ConcreteProduct1();
}
}
// 具体工厂2:实现了厂品的生成方法
class ConcreteFactory2 implements AbstractFactory {
public Product newProduct() {
System.out.println("具体工厂2生成-->具体产品2...");
return new ConcreteProduct2();
}
}
package FactoryMethod;
import javax.xml.parsers.*;
import org.w3c.dom.*;
import java.io.*;
class ReadXML1 {
// 该方法用于从XML配置文件中提取具体类类名,并返回一个实例对象
public static Object getObject() {
try {
// 创建文档对象
DocumentBuilderFactory dFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = dFactory.newDocumentBuilder();
Document doc;
doc = builder.parse(new File("src/FactoryMethod/config1.xml"));
// 获取包含类名的文本节点
NodeList nl = doc.getElementsByTagName("className");
Node classNode = nl.item(0).getFirstChild();
String cName = "FactoryMethod." + classNode.getNodeValue();
// System.out.println("新类名:"+cName);
// 通过类名生成实例对象并将其返回
Class<?> c = Class.forName(cName);
Object obj = c.newInstance();
return obj;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
}
模式定义: 提供一个创建一组相关或相互依赖对象的接口,且访问类无须指定所要产品的具体类就能得到同族的不同等级的产品的模式结构。
使用抽象工厂模式一般要满足以下条件:
模式优点:
模式缺点:
应用场景:
代码实现:
(1) 抽象工厂:提供了产品的生成方法。
interface AbstractFactory {
public Product1 newProduct1();
public Product2 newProduct2();
}
(2) 具体工厂:实现了产品的生成方法。
class ConcreteFactory1 implements AbstractFactory {
public Product1 newProduct1() {
System.out.println("具体工厂 1 生成-->具体产品 11...");
return new ConcreteProduct11();
}
public Product2 newProduct2() {
System.out.println("具体工厂 1 生成-->具体产品 21...");
return new ConcreteProduct21();
}
}
模式定义: 将一个类的接口转换成客户希望的另外一个接口,使得原本由于接口不兼容而不能一起工作的那些类能一起工作。适配器模式分为类结构型模式和对象结构型模式两种,前者类之间的耦合度比后者高,且要求程序员了解现有组件库中的相关组件的内部结构,所以应用相对较少些。
模式优点:
模式缺点:
应用场景:
代码实现:
(1) 类适配器模式的代码如下。
package adapter;
// 目标接口
interface Target {
public void request();
}
// 适配者接口
class Adaptee {
public void specificRequest() {
System.out.println("适配者中的业务代码被调用!");
}
}
// 类适配器类
class ClassAdapter extends Adaptee implements Target {
public void request() {
specificRequest();
}
}
// 客户端代码
public class ClassAdapterTest {
public static void main(String[] args) {
System.out.println("类适配器模式测试:");
Target target = new ClassAdapter();
target.request();
}
}
(2)对象适配器模式的代码如下。
package adapter;
// 对象适配器类
class ObjectAdapter implements Target {
private Adaptee adaptee;
public ObjectAdapter(Adaptee adaptee) {
this.adaptee=adaptee;
}
public void request() {
adaptee.specificRequest();
}
}
// 客户端代码
public class ObjectAdapterTest {
public static void main(String[] args)
{
System.out.println("对象适配器模式测试:");
Adaptee adaptee = new Adaptee();
Target target = new ObjectAdapter(adaptee);
target.request();
}
}
模式定义: 有时又叫作部分-整体模式,它是一种将对象组合成树状的层次结构的模式,用来表示“部分-整体”的关系,使用户对单个对象和组合对象具有一致的访问性。
模式优点:
模式缺点:
应用场景:
代码实现:
package composite;
import java.util.ArrayList;
public class CompositePattern {
public static void main(String[] args) {
Component c0=new Composite();
Component c1=new Composite();
Component leaf1=new Leaf("1");
Component leaf2=new Leaf("2");
Component leaf3=new Leaf("3");
c0.add(leaf1);
c0.add(c1);
c1.add(leaf2);
c1.add(leaf3);
c0.operation();
}
}
// 抽象构件
interface Component {
public void add(Component c);
public void remove(Component c);
public Component getChild(int i);
public void operation();
}
// 树叶构件
class Leaf implements Component {
private String name;
public Leaf(String name) {
this.name=name;
}
public void add(Component c) {}
public void remove(Component c) {}
public Component getChild(int i) {
return null;
}
public void operation() {
System.out.println("树叶"+name+":被访问!");
}
}
// 树枝构件
class Composite implements Component {
private ArrayList<Component> children=new ArrayList<Component>();
public void add(Component c) {
children.add(c);
}
public void remove(Component c) {
children.remove(c);
}
public Component getChild(int i) {
return children.get(i);
}
public void operation() {
for(Object obj:children) {
((Component)obj).operation();
}
}
}
模式定义: 在不改变现有对象结构的情况下,动态地给该对象增加一些职责(即增加其额外功能)的模式。
模式优点:
模式缺点:
应用场景:
代码实现:
package decorator;
public class DecoratorPattern {
public static void main(String[] args) {
Component p=new ConcreteComponent();
p.operation();
System.out.println("---------------------------------");
Component d=new ConcreteDecorator(p);
d.operation();
}
}
// 抽象构件角色
interface Component {
public void operation();
}
// 具体构件角色
class ConcreteComponent implements Component {
public ConcreteComponent() {
System.out.println("创建具体构件角色");
}
public void operation() {
System.out.println("调用具体构件角色的方法operation()");
}
}
// 抽象装饰角色
class Decorator implements Component {
private Component component;
public Decorator(Component component) {
this.component=component;
}
public void operation() {
component.operation();
}
}
// 具体装饰角色
class ConcreteDecorator extends Decorator {
public ConcreteDecorator(Component component) {
super(component);
}
public void operation() {
super.operation();
addedFunction();
}
public void addedFunction() {
System.out.println("为具体构件角色增加额外的功能addedFunction()");
}
}
模式定义: 一种通过为多个复杂的子系统提供一个一致的接口,而使这些子系统更加容易被访问的模式。该模式对外有一个统一接口,外部应用程序不用关心内部子系统的具体的细节,这样会大大降低应用程序的复杂度,提高了程序的可维护性。
模式优点:
模式缺点:
应用场景:
代码实现:
package facade;
public class FacadePattern{
public static void main(String[] args) {
Facade f=new Facade();
f.method();
}
}
// 外观角色
class Facade {
private SubSystem01 obj1=new SubSystem01();
private SubSystem02 obj2=new SubSystem02();
private SubSystem03 obj3=new SubSystem03();
public void method() {
obj1.method1();
obj2.method2();
obj3.method3();
}
}
// 子系统角色
class SubSystem01 {
public void method1()
{
System.out.println("子系统01的method1()被调用!");
}
}
// 子系统角色
class SubSystem02 {
public void method2() {
System.out.println("子系统02的method2()被调用!");
}
}
// 子系统角色
class SubSystem03 {
public void method3() {
System.out.println("子系统03的method3()被调用!");
}
}
模式定义: 将抽象与实现分离,使它们可以独立变化。它是用组合关系代替继承关系来实现,从而降低了抽象和实现这两个可变维度的耦合度。
模式优点:
模式缺点:
应用场景:
代码实现:
package bridge;
public class BridgeTest {
public static void main(String[] args) {
Implementor imple=new ConcreteImplementorA();
Abstraction abs=new RefinedAbstraction(imple);
abs.Operation();
}
}
// 实现化角色
interface Implementor {
public void OperationImpl();
}
// 具体实现化角色
class ConcreteImplementorA implements Implementor {
public void OperationImpl() {
System.out.println("具体实现化(Concrete Implementor)角色被访问" );
}
}
// 抽象化角色
abstract class Abstraction {
protected Implementor imple;
protected Abstraction(Implementor imple) {
this.imple=imple;
}
public abstract void Operation();
}
// 扩展抽象化角色
class RefinedAbstraction extends Abstraction {
protected RefinedAbstraction(Implementor imple) {
super(imple);
}
public void Operation() {
System.out.println("扩展抽象化(Refined Abstraction)角色被访问" );
imple.OperationImpl();
}
}
模式定义: 运用共享技术来有效地支持大量细粒度对象的复用。它通过共享已经存在的对象来大幅度减少需要创建的对象数量、避免大量相似类的开销,从而提高系统资源的利用率。
模式优点:
模式缺点:
应用场景:
代码实现:
package flyweight;
import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
import javax.swing.*;
public class WzqGame {
public static void main(String[] args) {
new Chessboard();
}
}
// 棋盘
class Chessboard extends MouseAdapter {
WeiqiFactory wf;
JFrame f;
Graphics g;
JRadioButton wz;
JRadioButton bz;
private final int x=50;
private final int y=50;
private final int w=40; // 小方格宽度和高度
private final int rw=400; // 棋盘宽度和高度
Chessboard() {
wf=new WeiqiFactory();
f=new JFrame("享元模式在五子棋游戏中的应用");
f.setBounds(100,100,500,550);
f.setVisible(true);
f.setResizable(false);
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel SouthJP=new JPanel();
f.add("South",SouthJP);
wz=new JRadioButton("白子");
bz=new JRadioButton("黑子",true);
ButtonGroup group=new ButtonGroup();
group.add(wz);
group.add(bz);
SouthJP.add(wz);
SouthJP.add(bz);
JPanel CenterJP=new JPanel();
CenterJP.setLayout(null);
CenterJP.setSize(500, 500);
CenterJP.addMouseListener(this);
f.add("Center",CenterJP);
try {
Thread.sleep(500);
}
catch(InterruptedException e) {
e.printStackTrace();
}
g=CenterJP.getGraphics();
g.setColor(Color.BLUE);
g.drawRect(x, y, rw, rw);
for(int i=1;i<10;i++) {
// 绘制第i条竖直线
g.drawLine(x+(i*w),y,x+(i*w),y+rw);
// 绘制第i条水平线
g.drawLine(x,y+(i*w),x+rw,y+(i*w));
}
}
public void mouseClicked(MouseEvent e) {
Point pt=new Point(e.getX()-15,e.getY()-15);
if(wz.isSelected()) {
ChessPieces c1=wf.getChessPieces("w");
c1.DownPieces(g,pt);
}
else if(bz.isSelected()) {
ChessPieces c2=wf.getChessPieces("b");
c2.DownPieces(g,pt);
}
}
}
// 抽象享元角色:棋子
interface ChessPieces {
public void DownPieces(Graphics g,Point pt); // 下子
}
// 具体享元角色:白子
class WhitePieces implements ChessPieces {
public void DownPieces(Graphics g,Point pt) {
g.setColor(Color.WHITE);
g.fillOval(pt.x,pt.y,30,30);
}
}
// 具体享元角色:黑子
class BlackPieces implements ChessPieces {
public void DownPieces(Graphics g,Point pt) {
g.setColor(Color.BLACK);
g.fillOval(pt.x,pt.y,30,30);
}
}
// 享元工厂角色
class WeiqiFactory {
private ArrayList<ChessPieces> qz;
public WeiqiFactory() {
qz=new ArrayList<ChessPieces>();
ChessPieces w=new WhitePieces();
qz.add(w);
ChessPieces b=new BlackPieces();
qz.add(b);
}
public ChessPieces getChessPieces(String type) {
if(type.equalsIgnoreCase("w")) {
return (ChessPieces)qz.get(0);
}
else if(type.equalsIgnoreCase("b")) {
return (ChessPieces)qz.get(1);
}
else {
return null;
}
}
}
模式定义: 由于某些原因需要给某对象提供一个代理以控制对该对象的访问。这时,访问对象不适合或者不能直接引用目标对象,代理对象作为访问对象和目标对象之间的中介。
模式优点:
模式缺点:
应用场景:
代码实现:
package proxy;
public class ProxyTest {
public static void main(String[] args) {
Proxy proxy = new Proxy();
proxy.Request();
}
}
// 抽象主题
interface Subject {
void Request();
}
// 真实主题
class RealSubject implements Subject {
public void Request() {
System.out.println("访问真实主题方法...");
}
}
// 代理
class Proxy implements Subject {
private RealSubject realSubject;
public void Request() {
if (realSubject == null) {
realSubject = new RealSubject();
}
preRequest();
realSubject.Request();
postRequest();
}
public void preRequest() {
System.out.println("访问真实主题之前的预处理。");
}
public void postRequest() {
System.out.println("访问真实主题之后的后续处理。");
}
}
模式定义: 定义一个操作中的算法骨架,而将算法的一些步骤延迟到子类中,使得子类可以不改变该算法结构的情况下重定义该算法的某些特定步骤。它是一种类行为型模式。
模式优点:
模式缺点:
应用场景:
代码实现:
package templateMethod;
public class TemplateMethodPattern {
public static void main(String[] args)
{
AbstractClass tm=new ConcreteClass();
tm.TemplateMethod();
}
}
// 抽象类
abstract class AbstractClass
{
public void TemplateMethod() { // 模板方法
SpecificMethod();
abstractMethod1();
abstractMethod2();
}
public void SpecificMethod() { // 具体方法
System.out.println("抽象类中的具体方法被调用...");
}
public abstract void abstractMethod1(); // 抽象方法1
public abstract void abstractMethod2(); // 抽象方法2
}
// 具体子类
class ConcreteClass extends AbstractClass {
public void abstractMethod1() {
System.out.println("抽象方法1的实现被调用...");
}
public void abstractMethod2() {
System.out.println("抽象方法2的实现被调用...");
}
}
模式定义: 给分析对象定义一个语言,并定义该语言的文法表示,再设计一个解析器来解释语言中的句子。也就是说,用编译语言的方式来分析应用中的实例。这种模式实现了文法表达式处理的接口,该接口解释一个特定的上下文。
模式优点:
模式缺点:
应用场景:
代码实现:
解释器模式实现的关键是定义文法规则、设计终结符类与非终结符类、画出结构图,必要时构建语法树,其代码结构如下:
// 抽象表达式类
interface AbstractExpression {
public Object interpret(String info); // 解释方法
}
// 终结符表达式类
class TerminalExpression implements AbstractExpression {
public Object interpret(String info) {
// 对终结符表达式的处理
}
}
// 非终结符表达式类
class NonterminalExpression implements AbstractExpression {
private AbstractExpression exp1;
private AbstractExpression exp2;
public Object interpret(String info) {
// 非对终结符表达式的处理
}
}
// 环境类
class Context {
private AbstractExpression exp;
public Context() {
// 数据初始化
}
public void operation(String info) {
// 调用相关表达式类的解释方法
}
}
模式定义: 该模式定义了一系列算法,并将每个算法封装起来,使它们可以相互替换,且算法的变化不会影响使用算法的客户。策略模式属于对象行为模式,它通过对算法进行封装,把使用算法的责任和算法的实现分割开来,并委派给不同的对象对这些算法进行管理。
模式优点:
模式缺点:
应用场景:
代码实现:
package strategy;
public class StrategyPattern {
public static void main(String[] args) {
Context c=new Context();
Strategy s=new ConcreteStrategyA();
c.setStrategy(s);
c.strategyMethod();
System.out.println("-----------------");
s=new ConcreteStrategyB();
c.setStrategy(s);
c.strategyMethod();
}
}
// 抽象策略类
interface Strategy {
public void strategyMethod(); // 策略方法
}
// 具体策略类A
class ConcreteStrategyA implements Strategy {
public void strategyMethod() {
System.out.println("具体策略A的策略方法被访问!");
}
}
// 具体策略类B
class ConcreteStrategyB implements Strategy {
public void strategyMethod() {
System.out.println("具体策略B的策略方法被访问!");
}
}
// 环境类
class Context {
private Strategy strategy;
public Strategy getStrategy() {
return strategy;
}
public void setStrategy(Strategy strategy) {
this.strategy=strategy;
}
public void strategyMethod() {
strategy.strategyMethod();
}
}
模式定义: 对有状态的对象,把复杂的“判断逻辑”提取到不同的状态对象中,允许状态对象在其内部状态发生改变时改变其行为。
模式优点:
模式缺点:
应用场景:
代码实现:
package state;
public class StatePatternClient {
public static void main(String[] args) {
Context context=new Context(); // 创建环境
context.Handle(); // 处理请求
context.Handle();
context.Handle();
context.Handle();
}
}
// 环境类
class Context {
private State state;
// 定义环境类的初始状态
public Context() {
this.state=new ConcreteStateA();
}
// 设置新状态
public void setState(State state) {
this.state=state;
}
// 读取状态
public State getState() {
return(state);
}
// 对请求做处理
public void Handle() {
state.Handle(this);
}
}
// 抽象状态类
abstract class State {
public abstract void Handle(Context context);
}
// 具体状态A类
class ConcreteStateA extends State {
public void Handle(Context context) {
System.out.println("当前状态是 A.");
context.setState(new ConcreteStateB());
}
}
// 具体状态B类
class ConcreteStateB extends State {
public void Handle(Context context) {
System.out.println("当前状态是 B.");
context.setState(new ConcreteStateA());
}
}
模式定义: 多个对象间存在一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。这种模式有时又称作发布-订阅模式、模型-视图模式。
模式优点:
模式缺点:
应用场景:
代码实现:
package observer;
import java.util.*;
public class ObserverPattern {
public static void main(String[] args) {
Subject subject=new ConcreteSubject();
Observer obs1=new ConcreteObserver1();
Observer obs2=new ConcreteObserver2();
subject.add(obs1);
subject.add(obs2);
subject.notifyObserver();
}
}
// 抽象目标
abstract class Subject {
protected List<Observer> observers=new ArrayList<Observer>();
// 增加观察者方法
public void add(Observer observer) {
observers.add(observer);
}
// 删除观察者方法
public void remove(Observer observer) {
observers.remove(observer);
}
public abstract void notifyObserver(); // 通知观察者方法
}
// 具体目标
class ConcreteSubject extends Subject {
public void notifyObserver() {
System.out.println("具体目标发生改变...");
System.out.println("--------------");
for(Object obs:observers) {
((Observer)obs).response();
}
}
}
// 抽象观察者
interface Observer {
void response(); // 反应
}
// 具体观察者1
class ConcreteObserver1 implements Observer {
public void response() {
System.out.println("具体观察者1作出反应!");
}
}
// 具体观察者1
class ConcreteObserver2 implements Observer {
public void response() {
System.out.println("具体观察者2作出反应!");
}
}
模式定义: 在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,以便以后当需要时能将该对象恢复到原先保存的状态。该模式又叫快照模式。
模式优点:
模式缺点:
应用场景:
代码实现:
package memento;
public class MementoPattern {
public static void main(String[] args) {
Originator or=new Originator();
Caretaker cr=new Caretaker();
or.setState("S0");
System.out.println("初始状态:"+or.getState());
cr.setMemento(or.createMemento()); // 保存状态
or.setState("S1");
System.out.println("新的状态:"+or.getState());
or.restoreMemento(cr.getMemento()); // 恢复状态
System.out.println("恢复状态:"+or.getState());
}
}
// 备忘录
class Memento {
private String state;
public Memento(String state) {
this.state=state;
}
public void setState(String state) {
this.state=state;
}
public String getState() {
return state;
}
}
// 发起人
class Originator {
private String state;
public void setState(String state) {
this.state=state;
}
public String getState() {
return state;
}
public Memento createMemento() {
return new Memento(state);
}
public void restoreMemento(Memento m) {
this.setState(m.getState());
}
}
// 管理者
class Caretaker {
private Memento memento;
public void setMemento(Memento m) {
memento=m;
}
public Memento getMemento() {
return memento;
}
}
模式定义: 定义一个中介对象来封装一系列对象之间的交互,使原有对象之间的耦合松散,且可以独立地改变它们之间的交互。中介者模式又叫调停模式,它是迪米特法则的典型应用。
模式优点:
模式缺点:
应用场景:
代码实现:
package mediator;
import java.util.*;
public class MediatorPattern {
public static void main(String[] args) {
Mediator md=new ConcreteMediator();
Colleague c1,c2;
c1=new ConcreteColleague1();
c2=new ConcreteColleague2();
md.register(c1);
md.register(c2);
c1.send();
System.out.println("-------------");
c2.send();
}
}
// 抽象中介者
abstract class Mediator {
public abstract void register(Colleague colleague);
public abstract void relay(Colleague cl); // 转发
}
// 具体中介者
class ConcreteMediator extends Mediator {
private List<Colleague> colleagues=new ArrayList<Colleague>();
public void register(Colleague colleague) {
if(!colleagues.contains(colleague)) {
colleagues.add(colleague);
colleague.setMedium(this);
}
}
public void relay(Colleague cl) {
for(Colleague ob:colleagues) {
if(!ob.equals(cl)) {
((Colleague)ob).receive();
}
}
}
}
// 抽象同事类
abstract class Colleague {
protected Mediator mediator;
public void setMedium(Mediator mediator) {
this.mediator=mediator;
}
public abstract void receive();
public abstract void send();
}
// 具体同事类
class ConcreteColleague1 extends Colleague {
public void receive() {
System.out.println("具体同事类1收到请求。");
}
public void send() {
System.out.println("具体同事类1发出请求。");
mediator.relay(this); //请中介者转发
}
}
// 具体同事类
class ConcreteColleague2 extends Colleague {
public void receive() {
System.out.println("具体同事类2收到请求。");
}
public void send() {
System.out.println("具体同事类2发出请求。");
mediator.relay(this); //请中介者转发
}
}
模式定义: 将一个请求封装为一个对象,使发出请求的责任和执行请求的责任分割开。这样两者之间通过命令对象进行沟通,这样方便将命令对象进行储存、传递、调用、增加与管理。
模式优点:
模式缺点:
应用场景:
代码实现:
package command;
public class CommandPattern {
public static void main(String[] args) {
Command cmd=new ConcreteCommand();
Invoker ir=new Invoker(cmd);
System.out.println("客户访问调用者的call()方法...");
ir.call();
}
}
// 调用者
class Invoker {
private Command command;
public Invoker(Command command) {
this.command=command;
}
public void setCommand(Command command) {
this.command=command;
}
public void call() {
System.out.println("调用者执行命令command...");
command.execute();
}
}
// 抽象命令
interface Command {
public abstract void execute();
}
// 具体命令
class ConcreteCommand implements Command {
private Receiver receiver;
ConcreteCommand() {
receiver=new Receiver();
}
public void execute() {
receiver.action();
}
}
// 接收者
class Receiver {
public void action() {
System.out.println("接收者的action()方法被调用...");
}
}
模式定义: 将作用于某种数据结构中的各元素的操作分离出来封装成独立的类,使其在不改变数据结构的前提下可以添加作用于这些元素的新的操作,为数据结构中的每个元素提供多种访问方式。它将对数据的操作与数据结构进行分离,是行为类模式中最复杂的一种模式。
模式优点:
模式缺点:
应用场景:
代码实现:
package visitor;
import java.util.*;
public class VisitorPattern {
public static void main(String[] args) {
ObjectStructure os=new ObjectStructure();
os.add(new ConcreteElementA());
os.add(new ConcreteElementB());
Visitor visitor=new ConcreteVisitorA();
os.accept(visitor);
System.out.println("------------------------");
visitor=new ConcreteVisitorB();
os.accept(visitor);
}
}
// 抽象访问者
interface Visitor {
void visit(ConcreteElementA element);
void visit(ConcreteElementB element);
}
// 具体访问者A类
class ConcreteVisitorA implements Visitor {
public void visit(ConcreteElementA element) {
System.out.println("具体访问者A访问-->"+element.operationA());
}
public void visit(ConcreteElementB element) {
System.out.println("具体访问者A访问-->"+element.operationB());
}
}
// 具体访问者B类
class ConcreteVisitorB implements Visitor {
public void visit(ConcreteElementA element) {
System.out.println("具体访问者B访问-->"+element.operationA());
}
public void visit(ConcreteElementB element) {
System.out.println("具体访问者B访问-->"+element.operationB());
}
}
// 抽象元素类
interface Element {
void accept(Visitor visitor);
}
// 具体元素A类
class ConcreteElementA implements Element {
public void accept(Visitor visitor) {
visitor.visit(this);
}
public String operationA() {
return "具体元素A的操作。";
}
}
// 具体元素B类
class ConcreteElementB implements Element {
public void accept(Visitor visitor) {
visitor.visit(this);
}
public String operationB() {
return "具体元素B的操作。";
}
}
// 对象结构角色
class ObjectStructure {
private List<Element> list=new ArrayList<Element>();
public void accept(Visitor visitor) {
Iterator<Element> i=list.iterator();
while(i.hasNext()) {
((Element) i.next()).accept(visitor);
}
}
public void add(Element element) {
list.add(element);
}
public void remove(Element element) {
list.remove(element);
}
}
模式定义: 为了避免请求发送者与多个请求处理者耦合在一起,将所有请求的处理者通过前一对象记住其下一个对象的引用而连成一条链;当有请求发生时,可将请求沿着这条链传递,直到有对象处理它为止。
模式优点:
模式缺点:
应用场景:
代码实现:
package chainOfResponsibility;
public class ChainOfResponsibilityPattern {
public static void main(String[] args) {
// 组装责任链
Handler handler1=new ConcreteHandler1();
Handler handler2=new ConcreteHandler2();
handler1.setNext(handler2);
// 提交请求
handler1.handleRequest("two");
}
}
// 抽象处理者角色
abstract class Handler {
private Handler next;
public void setNext(Handler next) {
this.next=next;
}
public Handler getNext() {
return next;
}
// 处理请求的方法
public abstract void handleRequest(String request);
}
// 具体处理者角色1
class ConcreteHandler1 extends Handler {
public void handleRequest(String request) {
if(request.equals("one")) {
System.out.println("具体处理者1负责处理该请求!");
}
else {
if(getNext()!=null) {
getNext().handleRequest(request);
}
else {
System.out.println("没有人处理该请求!");
}
}
}
}
// 具体处理者角色2
class ConcreteHandler2 extends Handler {
public void handleRequest(String request) {
if(request.equals("two")) {
System.out.println("具体处理者2负责处理该请求!");
}
else {
if(getNext()!=null) {
getNext().handleRequest(request);
}
else {
System.out.println("没有人处理该请求!");
}
}
}
}
模式定义: 提供一个对象来顺序访问聚合对象中的一系列数据,而不暴露聚合对象的内部表示。
模式优点:
模式缺点:
应用场景:
代码实现:
package iterator;
import java.util.*;
public class IteratorPattern {
public static void main(String[] args) {
Aggregate ag=new ConcreteAggregate();
ag.add("中山大学");
ag.add("华南理工");
ag.add("韶关学院");
System.out.print("聚合的内容有:");
Iterator it=ag.getIterator();
while(it.hasNext()) {
Object ob=it.next();
System.out.print(ob.toString()+"\t");
}
Object ob=it.first();
System.out.println("\nFirst:"+ob.toString());
}
}
// 抽象聚合
interface Aggregate {
public void add(Object obj);
public void remove(Object obj);
public Iterator getIterator();
}
// 具体聚合
class ConcreteAggregate implements Aggregate {
private List<Object> list=new ArrayList<Object>();
public void add(Object obj) {
list.add(obj);
}
public void remove(Object obj) {
list.remove(obj);
}
public Iterator getIterator() {
return(new ConcreteIterator(list));
}
}
// 抽象迭代器
interface Iterator {
Object first();
Object next();
boolean hasNext();
}
// 具体迭代器
class ConcreteIterator implements Iterator {
private List<Object> list=null;
private int index=-1;
public ConcreteIterator(List<Object> list) {
this.list=list;
}
public boolean hasNext() {
if(index<list.size()-1) {
return true;
}
else {
return false;
}
}
public Object first() {
index=0;
Object obj=list.get(index);;
return obj;
}
public Object next() {
Object obj=null;
if(this.hasNext()) {
obj=list.get(++index);
}
return obj;
}
}