设计模式分类
分类描述 | 模式名称 |
---|---|
创建型模式 提供了一种在创建对象的同时隐藏创建逻辑的方式 | 工厂模式(Factory Pattern) 抽象工厂模式(Abstract Factory Pattern) 单例模式(Singleton Pattern) 建造者模式(Build Pattern) 原型模式(ProtoType Pattern) |
结构型模式 关注类和对象的组合 | 适配器模式(Adapter Pattern) 桥接模式(Bridge Pattern) 过滤器模式(Filter、Criteria Pattern) 组合模式(Composite Pattern) 装饰器模式(Decorator Pattern) 外观模式(Facade Pattern) 享元模式(Flyweight Pattern) 代理模式(Proxy Pattern) |
行为型模式 关注对象之间的通信 | 责任链模式(Chain of Responsibility Pattern) 命令模式(Command Pattern) 解释器模式(Interpreter Patt) 迭代器模式(Iterator Pattern) 中介者模式(Mediator Pattern) 备忘录模式(Memento Pattern) 观察者模式(Observer Pattern) 状态模式(State Pattern) 空对象模式(Null Object Pattern) 策略模式(Strategy Pattern) 模板模式(Template Pattern) 访问者模式(Visitor Pattern) |
面向对象六大原则
原则 | 描述 |
---|---|
单一职责原则 | 一个类只负责一个功能领域中的相应职责 |
开闭原则 | 对象对于扩展时开放的,对于修改的封闭的 |
里氏替换原则 | 所有引用基类的地方必须能透明的使用其子类的对象 |
依赖倒置原则 | 高层模块不应该依赖低层模块,两者应该依赖其对象;抽象不应该依赖细节,细节应该依赖抽象 |
接口隔离原则 | 类间的依赖关系应该建立在最小的接口上 |
迪米特原则 | 也称最小知识原则。一个对象对其他对象有最小的了解。 |
设计模式的内容有点多,本文仅简单描述模式以及用代码简单举例,后续会更新常见设计模式的详解文章。
一、创建型模式
1、工厂模式(Factory Pattern)
适用于复杂对象的创建,通过定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法模式使一个类的实例化延迟到其子类。
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.demo);
//BitmapFactory.java
// 生成 Bitmap 对象的工厂类 BitmapFactory
public class BitmapFactory {
public static Bitmap decodeFile(String pathName) {
···
}
···
public static Bitmap decodeResource(Resources res, int id, Options opts) {
validate(opts);
Bitmap bm = null;
InputStream is = null;
try {
final TypedValue value = new TypedValue();
is = res.openRawResource(id, value);
bm = decodeResourceStream(res, value, is, null, opts);
}
return bm;
}
···
}
2、抽象工厂模式(Abstract Factory Pattern)
为访问类提供一个创建一组相关或相互依赖对象的接口,且访问类无须指定所要产品的具体类就能得到同族的不同等级的产品的模式结构;是工厂模式的升级版本,工厂方法模式只生产一个等级的产品,而抽象工厂模式可生产多个等级的产品。
public interface Button {}
public interface Border {}
public class MacButton implements Button {}
public class MacBorder implements Border {}
public class WinButton implements Button {}
public class WinBorder implements Border {}
public class MacFactory {
public static Button createButton() {
return new MacButton();
}
public static Border createBorder() {
return new MacBorder();
}
}
public class WinFactory {
public static Button createButton() {
return new WinButton();
}
public static Border createBorder() {
return new WinBorder();
}
}
3、单例模式(Singleton Pattern)
确保一个类只有一个实例,并自动实例化向整个系统提供这个实例,可以避免产生多个对象消耗资源。有懒汉式和饿汉式两种实现方式。
饿汉式单例(线程安全的)
public class Singleton {
private Singleton() {}
private static final Singleton single = new Singleton();
public static Singleton getInstance() {
return single;
}
//单例模式,构造器要私有化
private SingletonTest {
}
}
懒汉式单例
//有线程安全的问题,不推荐使用
public class SingletonTest {
public static SingletonTest singleton = null;
public static SingletonTest getInstance(){
if(singleton == null){
singleton = new SingletonTest();
}
return singleton;
}
//单例模式,构造器要私有化
private SingletonTest {
}
}
静态内部类实现单例
public class Singleton {
private static class SingleTonHoler{
private static Singleton INSTANCE = new Singleton();
}
public static Singleton getInstance(){
return SingleTonHoler.INSTANCE;
}
//单例模式,构造器要私有化
private SingletonTest {
}
}
静态内部类实现单例的优点:外部类加载时不需要立即加载内部类,内部类不被加载则不去初始化INSTANCE,故而不占内存。即当SingleTon第一次被加载时,并不需要去加载SingleTonHoler,只有当getInstance()方法第一次被调用时,才会去初始化INSTANCE,第一次调用getInstance()方法会导致虚拟机加载SingleTonHoler类,这种方法不仅能确保线程安全,也能保证单例的唯一性,同时也延迟了单例的实例化。
4、建造者模式(Build Pattern)
将一个复杂对象的构建与他的表示分离,使得同样的构建过程可以有不同的表示,适用于初始化的对象比较复杂且参数较多的情况。
AlertDialog.Builder builder = new AlertDialog.Builder(this)
.setTitle("Title")
.setMessage("Message");AlertDialog dialog = builder.create();
dialog.show();
//AlertDialog.java
public class AlertDialog extends Dialog implements DialogInterface {
···
public static class Builder {
private final AlertController.AlertParams P;
···
public Builder(Context context) {
this(context, resolveDialogTheme(context, ResourceId.ID_NULL));
}
···
public Builder setTitle(CharSequence title) {
P.mTitle = title;
return this;
}
···
public Builder setMessage(CharSequence message) {
P.mMessage = message;
return this;
}
···
public AlertDialog create() {
// Context has already been wrapped with the appropriate theme.
final AlertDialog dialog = new AlertDialog(P.mContext, 0, false);
P.apply(dialog.mAlert);
···
return dialog;
}
···
}
}
5、原型模式(ProtoType Pattern)
用原型模式实例指定创建对象的种类,并通过拷贝这些原型创建新的对象。
ArrayList<T> newArrayList = (ArrayList<T>) arrayList.clone();
//ArrayList.java
/** * Returns a shallow copy of this <tt>ArrayList</tt> instance. (The * elements themselves
are not copied.) * * @return a clone of this <tt>ArrayList</tt> instance */
public Object clone(){
try {
ArrayList<?> v = (ArrayList<?>) super.clone();
v.elementData = Arrays.copyOf(elementData, size);
v.modCount = 0;
return v;
} catch (CloneNotSupportedException e) {
// this shouldn't happen, since we are Cloneable
throw new InternalError(e);
}
}
二、结构型模式
6、适配器模式(Adapter Pattern)
把一个类的接口变成客户端所期待的另一种接口,从而使原来接口不匹配而无法一起工作的两个类能一起工作。
RecyclerView recyclerView = findViewById(R.id.recycler_view);
recyclerView.setAdapter(new MyAdapter());
private class MyAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
···
}
···
}
//RecyclerView.java
private void setAdapterInternal(@Nullable Adapter adapter, boolean compatibleWithPrevious,boolean removeAndRecycleViews) {
if (mAdapter != null) {
mAdapter.unregisterAdapterDataObserver(mObserver);
mAdapter.onDetachedFromRecyclerView(this);
}
if (!compatibleWithPrevious || removeAndRecycleViews) {
removeAndRecycleViews();
}
mAdapterHelper.reset();
final Adapter oldAdapter = mAdapter;
mAdapter = adapter;
if (adapter != null) {
adapter.registerAdapterDataObserver(mObserver);
adapter.onAttachedToRecyclerView(this);
}
if (mLayout != null) {
mLayout.onAdapterChanged(oldAdapter, mAdapter);
}
mRecycler.onAdapterChanged(oldAdapter, mAdapter, compatibleWithPrevious);
mState.mStructureChanged = true;
}
public final class Recycler {
...
@Nullable
ViewHolder tryGetViewHolderForPositionByDeadline(int position,boolean dryRun, long deadlineNs) {
···
ViewHolder holder = null;
···
if (holder == null) {
···
holder = mAdapter.createViewHolder(RecyclerView.this, type);
···
}
···
return holder;
}
}
public abstract static class Adapter<VH extends ViewHolder> {
···
@NonNull
public abstract VH onCreateViewHolder(@NonNull ViewGroup parent, int viewType);
@NonNull
public final VH createViewHolder(@NonNull ViewGroup parent, int viewType) {
try {
TraceCompat.beginSection(TRACE_CREATE_VIEW_TAG);
final VH holder = onCreateViewHolder(parent, viewType);
···
holder.mItemViewType = viewType;
return holder;
} finally {
TraceCompat.endSection();
}
}
···
}
7、桥接模式(Bridge Pattern)
将实现与抽象放在两个不同的层次中,使两个层次可以独立改变。基于类的最小设计原则,通过使用封装、聚合、继承等行为让不同的类承担不同的职责。主要特点是把抽象和行为实现分离开,从而可以保持各部分的独立性以及功能扩展。
/** "Implementor" */
interface DrawingAPI{
public void drawCircle(double x, double y, double radius);
}
/** "ConcreteImplementor" 1/2 */
class DrawingAPI1 implements DrawingAPI{
public void drawCircle(double x, double y, double radius){
System.out.printf("API1.circle at %f:%f radius %f\n", x, y, radius);
}
}
/** "ConcreteImplementor" 2/2 */
class DrawingAPI2 implements DrawingAPI{
public void drawCircle(double x, double y, double radius){
System.out.printf("API2.circle at %f:%f radius %f\n", x, y, radius);
}
}
/** "Abstraction" */
interface Shape{
public void draw();
// low-level
public void resizeByPercentage(double pct);
// high-level
}
/** "Refined Abstraction" */
class CircleShape implements Shape{
private double x, y, radius;
private DrawingAPI drawingAPI;
public CircleShape(double x, double y, double radius, DrawingAPI drawingAPI){
this.x = x;
this.y = y;
this.radius = radius;
this.drawingAPI = drawingAPI;
}
// low-level i.e. Implementation specific
public void draw(){
drawingAPI.drawCircle(x, y, radius);
}
// high-level i.e. Abstraction specific
public void resizeByPercentage(double pct){
radius *= pct;
}
}
/** "Client" */
class BridgePattern {
public static void main(String[] args) {
Shape[] shapes = new Shape[2];
shapes[0] = new CircleShape(1, 2, 3, new DrawingAPI1());
shapes[1] = new CircleShape(5, 7, 11, new DrawingAPI2());
for (Shape shape : shapes){
shape.resizeByPercentage(2.5);
shape.draw();
}
}
}
8、过滤器模式(Filter、Criteria Pattern)
允许开发人员使用不同的标准来过滤一组对象,通过逻辑运算以解耦的方式把他们连接起来。
//创建一个类,在该类上应用标准。
public class Person {
private String name;
private String gender;
private String maritalStatus;
public Person(String name,String gender,String maritalStatus){
this.name = name;
this.gender = gender;
this.maritalStatus = maritalStatus;
}
public String getName() {
return name;
}
public String getGender() {
return gender;
}
public String getMaritalStatus() {
return maritalStatus;
}
}
//为标准(Criteria)创建一个接口。
public interface Criteria {
public List<Person> meetCriteria(List<Person> persons);
}
//创建实现了 Criteria 接口的实体类。
public class CriteriaMale implements Criteria {
@Override
public List<Person> meetCriteria(List<Person> persons) {
List<Person> malePersons = new ArrayList<Person>();
for (Person person : persons) {
if(person.getGender().equalsIgnoreCase("MALE")){
malePersons.add(person);
}
}
return malePersons;
}
}
public class CriteriaFemale implements Criteria {
@Override
public List<Person> meetCriteria(List<Person> persons) {
List<Person> femalePersons = new ArrayList<Person>();
for (Person person : persons) {
if(person.getGender().equalsIgnoreCase("FEMALE")){
femalePersons.add(person);
}
}
return femalePersons;
}
}
public class CriteriaSingle implements Criteria {
@Override
public List<Person> meetCriteria(List<Person> persons) {
List<Person> singlePersons = new ArrayList<Person>();
for (Person person : persons) {
if(person.getMaritalStatus().equalsIgnoreCase("SINGLE")){
singlePersons.add(person);
}
}
return singlePersons;
}
}
public class AndCriteria implements Criteria {
private Criteria criteria;
private Criteria otherCriteria;
public AndCriteria(Criteria criteria, Criteria otherCriteria) {
this.criteria = criteria;
this.otherCriteria = otherCriteria;
}
@Override
public List<Person> meetCriteria(List<Person> persons) {
List<Person> firstCriteriaPersons = criteria.meetCriteria(persons);
return otherCriteria.meetCriteria(firstCriteriaPersons);
}
}
public class OrCriteria implements Criteria {
private Criteria criteria;
private Criteria otherCriteria;
public OrCriteria(Criteria criteria, Criteria otherCriteria) {
this.criteria = criteria;
this.otherCriteria = otherCriteria;
}
@Override
public List<Person> meetCriteria(List<Person> persons) {
List<Person> firstCriteriaItems = criteria.meetCriteria(persons);
List<Person> otherCriteriaItems = otherCriteria.meetCriteria(persons);
for (Person person : otherCriteriaItems) {
if(!firstCriteriaItems.contains(person)){
firstCriteriaItems.add(person);
}
}
return firstCriteriaItems;
}
}
//使用不同的标准(Criteria)和它们的结合来过滤 Person 对象的列表。
public class CriteriaPatternDemo {
public static void main(String[] args) {
List<Person> persons = new ArrayList<Person>();
persons.add(new Person("Robert","Male", "Single"));
persons.add(new Person("John","Male", "Married"));
persons.add(new Person("Laura","Female", "Married"));
persons.add(new Person("Diana","Female", "Single"));
persons.add(new Person("Mike","Male", "Single"));
persons.add(new Person("Bobby","Male", "Single"));
Criteria male = new CriteriaMale();
Criteria female = new CriteriaFemale();
Criteria single = new CriteriaSingle();
Criteria singleMale = new AndCriteria(single, male);
Criteria singleOrFemale = new OrCriteria(single, female);
System.out.println("Males: ");
printPersons(male.meetCriteria(persons));
System.out.println("\nFemales: ");
printPersons(female.meetCriteria(persons));
System.out.println("\nSingle Males: ");
printPersons(singleMale.meetCriteria(persons));
System.out.println("\nSingle Or Females: ");
printPersons(singleOrFemale.meetCriteria(persons));
}
public static void printPersons(List<Person> persons){
for (Person person : persons) {
System.out.println("Person : [ Name : " + person.getName()
+", Gender : " + person.getGender()
+", Marital Status : " + person.getMaritalStatus()
+" ]");
}
}
}
9、组合模式(Composite Pattern)
将对象组合成树形结构以表示“整体-部分”的层次关系,有透明组合模式和安全组合模式两种类型。
//创建 Employee 类,该类带有 Employee 对象的列表。
public class Employee {
private String name;
private String dept;
private int salary;
private List<Employee> subordinates;
//构造函数
public Employee(String name,String dept, int sal) {
this.name = name;
this.dept = dept;
this.salary = sal;
subordinates = new ArrayList<Employee>();
}
public void add(Employee e) {
subordinates.add(e);
}
public void remove(Employee e) {
subordinates.remove(e);
}
public List<Employee> getSubordinates(){
return subordinates;
}
public String toString(){
return ("Employee :[ Name : "+ name
+", dept : "+ dept + ", salary :"
+ salary+" ]");
}
}
//使用 Employee 类来创建和打印员工的层次结构。
public class CompositePatternDemo {
public static void main(String[] args) {
Employee CEO = new Employee("John","CEO", 30000);
Employee headSales = new Employee("Robert","Head Sales", 20000);
Employee headMarketing = new Employee("Michel","Head Marketing", 20000);
Employee clerk1 = new Employee("Laura","Marketing", 10000);
Employee clerk2 = new Employee("Bob","Marketing", 10000);
Employee salesExecutive1 = new Employee("Richard","Sales", 10000);
Employee salesExecutive2 = new Employee("Rob","Sales", 10000);
CEO.add(headSales);
CEO.add(headMarketing);
headSales.add(salesExecutive1);
headSales.add(salesExecutive2);
headMarketing.add(clerk1);
headMarketing.add(clerk2);
//打印该组织的所有员工
System.out.println(CEO);
for (Employee headEmployee : CEO.getSubordinates()) {
System.out.println(headEmployee);
for (Employee employee : headEmployee.getSubordinates()) {
System.out.println(employee);
}
}
}
}
10、装饰器模式(Decorator Pattern)
动态的给对象提供新的功能
//创建一个接口
public interface Shape {
void draw();
}
//创建实现接口的实体类。
public class Rectangle implements Shape {
@Override
public void draw() {
System.out.println("Shape: Rectangle");
}
}
public class Circle implements Shape {
@Override
public void draw() {
System.out.println("Shape: Circle");
}
}
//创建实现了 Shape 接口的抽象装饰类。
public abstract class ShapeDecorator implements Shape {
protected Shape decoratedShape;
public ShapeDecorator(Shape decoratedShape){
this.decoratedShape = decoratedShape;
}
public void draw(){
decoratedShape.draw();
}
}
//创建扩展了 ShapeDecorator 类的实体装饰类。
public class RedShapeDecorator extends ShapeDecorator {
public RedShapeDecorator(Shape decoratedShape) {
super(decoratedShape);
}
@Override
public void draw() {
decoratedShape.draw();
setRedBorder(decoratedShape);
}
private void setRedBorder(Shape decoratedShape){
System.out.println("Border Color: Red");
}
}
//使用 RedShapeDecorator 来装饰 Shape 对象。
public class DecoratorPatternDemo {
public static void main(String[] args) {
Shape circle = new Circle();
ShapeDecorator redCircle = new RedShapeDecorator(new Circle());
ShapeDecorator redRectangle = new RedShapeDecorator(new Rectangle());
//Shape redCircle = new RedShapeDecorator(new Circle());
//Shape redRectangle = new RedShapeDecorator(new Rectangle());
System.out.println("Circle with normal border");
circle.draw();
System.out.println("\nCircle of red border");
redCircle.draw();
System.out.println("\nRectangle of red border");
redRectangle.draw();
}
}
11、外观模式(Facade Pattern)
为子系统提供一个共同的对外访问接口
//创建一个接口。
public interface Shape {
void draw();
}
//创建实现接口的实体类
public class Rectangle implements Shape {
@Override
public void draw() {
System.out.println("Rectangle::draw()");
}
}
public class Circle implements Shape {
@Override
public void draw() {
System.out.println("Circle::draw()");
}
}
//创建一个外观类
public class ShapeMaker {
private Shape circle;
private Shape rectangle;
private Shape square;
public ShapeMaker() {
circle = new Circle();
rectangle = new Rectangle();
square = new Square();
}
public void drawCircle(){
circle.draw();
}
public void drawRectangle(){
rectangle.draw();
}
public void drawSquare(){
square.draw();
}
}
//使用该外观类画出各种类型的形状。
public class FacadePatternDemo {
public static void main(String[] args) {
ShapeMaker shapeMaker = new ShapeMaker();
shapeMaker.drawCircle();
shapeMaker.drawRectangle();
shapeMaker.drawSquare();
}
}
12、享元模式(Flyweight Pattern)
通过共享技术来有效支持大量细粒度的对象。是池技术的重要实现方式,String常量池、数据库连接池、缓冲池等等都是享元模式的应用。
//创建一个接口
public interface Shape {
void draw();
}
//创建实现接口的实体类。
public class Circle implements Shape {
private String color;
private int x;
private int y;
private int radius;
public Circle(String color){
this.color = color;
}
public void setX(int x) {
this.x = x;
}
public void setY(int y) {
this.y = y;
}
public void setRadius(int radius) {
this.radius = radius;
}
@Override
public void draw() {
System.out.println("Circle: Draw() [Color : " + color
+", x : " + x +", y :" + y +", radius :" + radius);
}
}
//创建一个工厂,生成基于给定信息的实体类的对象。
public class ShapeFactory {
private static final HashMap<String, Shape> circleMap = new HashMap<>();
public static Shape getCircle(String color) {
Circle circle = (Circle)circleMap.get(color);
if(circle == null) {
circle = new Circle(color);
circleMap.put(color, circle);
System.out.println("Creating circle of color : " + color);
}
return circle;
}
}
//使用该工厂,通过传递颜色信息来获取实体类的对象
public class FlyweightPatternDemo {
private static final String colors[] =
{ "Red", "Green", "Blue", "White", "Black" };
public static void main(String[] args) {
for(int i=0; i < 20; ++i) {
Circle circle =
(Circle)ShapeFactory.getCircle(getRandomColor());
circle.setX(getRandomX());
circle.setY(getRandomY());
circle.setRadius(100);
circle.draw();
}
}
private static String getRandomColor() {
return colors[(int)(Math.random()*colors.length)];
}
private static int getRandomX() {
return (int)(Math.random()*100 );
}
private static int getRandomY() {
return (int)(Math.random()*100);
}
}
13、代理模式(Proxy Pattern)
为其他的对象提供一种代理以控制对这个对象的访问。适用于当无法或不想直接访问某个对象时通过一个代理对象来间接访问,为了保证客户端使用的透明性,委托对象与代理对象要实现相同的接口。
//Context.java
public abstract class Context {
···
public abstract void startActivity(@RequiresPermission Intent intent);
···
}
//ContextWrapper.java
public class ContextWrapper extends Context {
Context mBase; // 代理类,实为 ContextImpl 对象
···
protected void attachBaseContext(Context base) {
if (mBase != null) {
throw new IllegalStateException("Base context already set");
}
mBase = base;
}
···
@Override
public void startActivity(Intent intent) {
mBase.startActivity(intent); // 核心工作交由给代理类对象 mBase 实现
}
···
}
//ContextImpl.java
// Context 的真正实现类
class ContextImpl extends Context {
...
@Override
public void startActivity(Intent intent) {
warnIfCallingFromSystemProcess();
startActivity(intent, null);
}
...
}
三、行为型模式
14、责任链模式(Chain of Responsibility Pattern)
使多个对象都有机会处理请求,从而避免了请求的发送者和接收者之间的耦合,将这些对象连成一条链,并沿着这条链传递该请求,直到有对象处理它为止。
//ViewGroup.java
@UiThread
public abstract class ViewGroup extends View implements ViewParent, ViewManager {
···
private boolean dispatchTransformedTouchEvent(MotionEvent event, boolean cancel,View child, int desiredPointerIdBits) {
final boolean handled;
···
final MotionEvent transformedEvent;
if (newPointerIdBits == oldPointerIdBits) {
if (child == null || child.hasIdentityMatrix()) {
if (child == null) {
handled = super.dispatchTouchEvent(event);
} else {
···
// 获取子 view 处理的结果
handled = child.dispatchTouchEvent(event);
}
return handled;
}
transformedEvent = MotionEvent.obtain(event);
} else {
transformedEvent = event.split(newPointerIdBits);
}
// Perform any necessary transformations and dispatch.
if (child == null) {
handled = super.dispatchTouchEvent(transformedEvent);
} else {
···
// 获取子 view 处理的结果
handled = child.dispatchTouchEvent(transformedEvent);
}
···
return handled;
}
···
}
15、命令模式(Command Pattern)
将命令请求封装为一个对象,使得可以用不同的请求来进行参数化。
//创建一个命令接口
public interface Order {
void execute();
}
//创建一个请求类
public class Stock {
private String name = "ABC";
private int quantity = 10;
public void buy(){
System.out.println("Stock [ Name: "+name+",
Quantity: " + quantity +" ] bought");
}
public void sell(){
System.out.println("Stock [ Name: "+name+",
Quantity: " + quantity +" ] sold");
}
}
//创建实现了 Order 接口的实体类
public class BuyStock implements Order {
private Stock abcStock;
public BuyStock(Stock abcStock){
this.abcStock = abcStock;
}
public void execute() {
abcStock.buy();
}
}
public class SellStock implements Order {
private Stock abcStock;
public SellStock(Stock abcStock){
this.abcStock = abcStock;
}
public void execute() {
abcStock.sell();
}
}
//创建命令调用类
public class Broker {
private List<Order> orderList = new ArrayList<Order>();
public void takeOrder(Order order){
orderList.add(order);
}
public void placeOrders(){
for (Order order : orderList) {
order.execute();
}
orderList.clear();
}
}
//使用 Broker 类来接受并执行命令。
public class CommandPatternDemo {
public static void main(String[] args) {
Stock abcStock = new Stock();
BuyStock buyStockOrder = new BuyStock(abcStock);
SellStock sellStockOrder = new SellStock(abcStock);
Broker broker = new Broker();
broker.takeOrder(buyStockOrder);
broker.takeOrder(sellStockOrder);
broker.placeOrders();
}
}
16、解释器模式(Interpreter Patt)
给定一个语言,定义它的文法表示,并定义一个解释器,这个解释器使用该标识来解释语言中的句子。
//创建一个表达式接口。
public interface Expression {
public boolean interpret(String context);
}
//创建实现了上述接口的实体类
public class TerminalExpression implements Expression {
private String data;
public TerminalExpression(String data){
this.data = data;
}
@Override
public boolean interpret(String context) {
if(context.contains(data)){
return true;
}
return false;
}
}
public class OrExpression implements Expression {
private Expression expr1 = null;
private Expression expr2 = null;
public OrExpression(Expression expr1, Expression expr2) {
this.expr1 = expr1;
this.expr2 = expr2;
}
@Override
public boolean interpret(String context) {
return expr1.interpret(context) || expr2.interpret(context);
}
}
public class AndExpression implements Expression {
private Expression expr1 = null;
private Expression expr2 = null;
public AndExpression(Expression expr1, Expression expr2) {
this.expr1 = expr1;
this.expr2 = expr2;
}
@Override
public boolean interpret(String context) {
return expr1.interpret(context) && expr2.interpret(context);
}
}
//InterpreterPatternDemo 使用 Expression 类来创建规则,并解析它们。
public class InterpreterPatternDemo {
//规则:Robert 和 John 是男性
public static Expression getMaleExpression(){
Expression robert = new TerminalExpression("Robert");
Expression john = new TerminalExpression("John");
return new OrExpression(robert, john);
}
//规则:Julie 是一个已婚的女性
public static Expression getMarriedWomanExpression(){
Expression julie = new TerminalExpression("Julie");
Expression married = new TerminalExpression("Married");
return new AndExpression(julie, married);
}
public static void main(String[] args) {
Expression isMale = getMaleExpression();
Expression isMarriedWoman = getMarriedWomanExpression();
System.out.println("John is male? " + isMale.interpret("John"));
System.out.println("Julie is a married women? "
+ isMarriedWoman.interpret("Married Julie"));
}
}
17、迭代器模式(Iterator Pattern)
提供一种方法顺序访问一个聚合对象中各个元素,而又无需暴露该对象的内部表示。
//创建接口
public interface Iterator {
public boolean hasNext();
public Object next();
}
public interface Container {
public Iterator getIterator();
}
//创建实现了 Container 接口的实体类。该类有实现了 Iterator 接口的内部类 NameIterator。
public class NameRepository implements Container {
public String[] names = {"Robert" , "John" ,"Julie" , "Lora"};
@Override
public Iterator getIterator() {
return new NameIterator();
}
private class NameIterator implements Iterator {
int index;
@Override
public boolean hasNext() {
if(index < names.length){
return true;
}
return false;
}
@Override
public Object next() {
if(this.hasNext()){
return names[index++];
}
return null;
}
}
}
//使用 NameRepository 来获取迭代器,并打印名字。
public class IteratorPatternDemo {
public static void main(String[] args) {
NameRepository namesRepository = new NameRepository();
for(Iterator iter = namesRepository.getIterator(); iter.hasNext();){
String name = (String)iter.next();
System.out.println("Name : " + name);
}
}
}
18、中介者模式(Mediator Pattern)
用来降低多个对象和类之间的通信复杂性,这种模式提供了一个中介类,该类通常处理不同类之间的通信,并支持松耦合,使代码易于维护。
//创建中介类
public class ChatRoom {
public static void showMessage(User user, String message){
System.out.println(new Date().toString()
+ " [" + user.getName() +"] : " + message);
}
}
//创建 user 类
public class User {
private String name;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public User(String name){
this.name = name;
}
public void sendMessage(String message){
ChatRoom.showMessage(this,message);
}
}
//使用 User 对象来显示他们之间的通信。
public class MediatorPatternDemo {
public static void main(String[] args) {
User robert = new User("Robert");
User john = new User("John");
robert.sendMessage("Hi! John!");
john.sendMessage("Hello! Robert!");
}
}
19、备忘录模式(Memento Pattern)
在不破环封闭的前提下,在对象之外保存对象的当前状态,并且在之后可以恢复到此状态。
//Activity.java
// 保存状态
protected void onSaveInstanceState(Bundle outState) {
// 存储当前窗口的视图树的状态
outState.putBundle(WINDOW_HIERARCHY_TAG, mWindow.saveHierarchyState());
outState.putInt(LAST_AUTOFILL_ID, mLastAutofillId);
// 存储 Fragment 的状态
Parcelable p = mFragments.saveAllState();
if (p != null) {
outState.putParcelable(FRAGMENTS_TAG, p);
}
if (mAutoFillResetNeeded) {
outState.putBoolean(AUTOFILL_RESET_NEEDED, true);
getAutofillManager().onSaveInstanceState(outState);
}
// 调用 ActivityLifecycleCallbacks 的 onSaveInstanceState 进行存储状态
getApplication().dispatchActivitySaveInstanceState(this, outState);
}
···
// onCreate 方法中恢复状态
protected void onCreate(@Nullable Bundle savedInstanceState) {
···
if (savedInstanceState != null) {
mAutoFillResetNeeded = savedInstanceState.getBoolean(AUTOFILL_RESET_NEEDED,false);
mLastAutofillId = savedInstanceState.getInt(LAST_AUTOFILL_ID,
View.LAST_APP_AUTOFILL_ID);
if (mAutoFillResetNeeded) {
getAutofillManager().onCreate(savedInstanceState);
}
Parcelable p = savedInstanceState.getParcelable(FRAGMENTS_TAG);
mFragments.restoreAllState(p, mLastNonConfigurationInstances != null ? mLastNonConfigurationInstances.fragments : null);
}
mFragments.dispatchCreate();
getApplication().dispatchActivityCreated(this, savedInstanceState);
···
mRestoredFromBundle = savedInstanceState != null;
mCalled = true;
}
//ActivityThread.java
@Override
public void handleStartActivity(ActivityClientRecord r,PendingTransactionActions pendingActions) {
final Activity activity = r.activity;
···
// Start
activity.performStart("handleStartActivity");
r.setState(ON_START);
···
// Restore instance state
if (pendingActions.shouldRestoreInstanceState()) {
if (r.isPersistable()) {
if (r.state != null || r.persistentState != null) {
mInstrumentation.callActivityOnRestoreInstanceState(activity, r.state,
r.persistentState);
}
} else if (r.state != null) {
mInstrumentation.callActivityOnRestoreInstanceState(activity, r.state);
}
}
···
}
20、观察者模式(Observer Pattern)
定义对象间一种一对多的依赖关系,使得每当一个对象改变状态,所有依赖于他的对象都会得到通知并被自动更新。
MyAdapter adapter = new MyAdapter();
recyclerView.setAdapter(adapter);
adapter.notifyDataSetChanged();
//RecyclerView.java
private final RecyclerViewDataObserver mObserver = new RecyclerViewDataObserver();
private void setAdapterInternal(@Nullable Adapter adapter, boolean compatibleWithPrevious,
boolean removeAndRecycleViews) {
···
mAdapter = adapter;
if (adapter != null) {
adapter.registerAdapterDataObserver(mObserver);
adapter.onAttachedToRecyclerView(this);
}
···
}
···
public abstract static class Adapter<VH extends ViewHolder> {
private final AdapterDataObservable mObservable = new AdapterDataObservable();
···
public void registerAdapterDataObserver(@NonNull AdapterDataObserver observer) {
mObservable.registerObserver(observer);
}
···
public final void notifyDataSetChanged() {
mObservable.notifyChanged();
}
}
static class AdapterDataObservable extends Observable<AdapterDataObserver> {
···
public void notifyChanged() {
for (int i = mObservers.size() - 1; i >= 0; i--) {
mObservers.get(i).onChanged();
}
}
···
}
private class RecyclerViewDataObserver extends AdapterDataObserver {
···
@Override
public void onChanged() {
assertNotInLayoutOrScroll(null);
mState.mStructureChanged = true;
processDataSetCompletelyChanged(true);
if (!mAdapterHelper.hasPendingUpdates()) {
requestLayout();
}
}
···
}
21、状态模式(State Pattern)
类的行为是基于他的状态改变的,在状态模式中我们创建表示各种状态的对象和一个行为随着状态对象改变而改变的context对象。
public interface State {
public void doAction(Context context);
}
//实现类
public class StartState implements State {
public void doAction(Context context) {
System.out.println("Player is in start state");
context.setState(this);
}
public String toString(){
return "Start State";
}
}
public class StopState implements State {
public void doAction(Context context) {
System.out.println("Player is in stop state");
context.setState(this);
}
public String toString(){
return "Stop State";
}
}
//Context类public class Context {
private State state;
public Context(){
state = null;
}
public void setState(State state){
this.state = state;
}
public State getState(){
return state;
}
}
//使用 Context 来查看当状态 State 改变时的行为变化。
public class StatePatternDemo {
public static void main(String[] args) {
Context context = new Context();
StartState startState = new StartState();
startState.doAction(context);
System.out.println(context.getState().toString());
StopState stopState = new StopState();
stopState.doAction(context);
System.out.println(context.getState().toString());
}
}
22、空对象模式(Null Object Pattern)
一个空对象取代Null对象实例的检查,Null对象不是检查空值,而是反应一个不做任何动作的关系,这样的Null对象也可以在数据不可用的时候提供默认的行为。在空对象模式中,我们创建个指定各种要执行的操作的抽象类和扩展该类的实体类,还创建一个未对该类做任何实现的空对象类,该空对象类将无缝地使用在需要检查空值的地方。
//创建一个抽象类
public abstract class AbstractCustomer {
protected String name;
public abstract boolean isNil();
public abstract String getName();
}
//创建扩展了上述类的实体类
public class RealCustomer extends AbstractCustomer {
public RealCustomer(String name) {
this.name = name;
}
@Override
public String getName() {
return name;
}
@Override
public boolean isNil() {
return false;
}
}
public class NullCustomer extends AbstractCustomer {
@Override
public String getName() {
return "Not Available in Customer Database";
}
@Override
public boolean isNil() {
return true;
}
}
//创建 CustomerFactory 类
public class CustomerFactory {
public static final String[] names = {"Rob", "Joe", "Julie"};
public static AbstractCustomer getCustomer(String name){
for (int i = 0; i < names.length; i++) {
if (names[i].equalsIgnoreCase(name)){
return new RealCustomer(name);
}
}
return new NullCustomer();
}
}
//使用 CustomerFactory,基于客户传递的名字,来获取 RealCustomer 或 NullCustomer 对象
public class NullPatternDemo {
public static void main(String[] args) {
AbstractCustomer customer1 = CustomerFactory.getCustomer("Rob");
AbstractCustomer customer2 = CustomerFactory.getCustomer("Bob");
AbstractCustomer customer3 = CustomerFactory.getCustomer("Julie");
AbstractCustomer customer4 = CustomerFactory.getCustomer("Laura");
System.out.println("Customers");
System.out.println(customer1.getName());
System.out.println(customer2.getName());
System.out.println(customer3.getName());
System.out.println(customer4.getName());
}
}
23、策略模式(Strategy Pattern)
定义了一系列算法并封装起来,提供针对某一类型问题的多种处理方式。
// 匀速
animation.setInterpolator(new LinearInterpolator());// 加速
animation.setInterpolator(new AccelerateInterpolator());
···
//BaseInterpolator.java
/** * An abstract class which is extended by default interpolators. */
abstract public class BaseInterpolator implements Interpolator {
private @Config int mChangingConfiguration;
/** * @hide */
public @Config int getChangingConfiguration() {
return mChangingConfiguration;
}
void setChangingConfiguration(@Config int changingConfiguration) {
mChangingConfiguration = changingConfiguration;
}
}
//LinearInterpolator.java
@HasNativeInterpolatorpublic class LinearInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {
···
}
//AccelerateInterpolator.java
@HasNativeInterpolator
public class AccelerateInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {
···
}
24、模板模式(Template Pattern)
定义一个操作中的算法的骨架,而将一些步骤延迟到子类中。模板方法使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。在模板模式中,一个抽象类公开定义了执行它的方法的方式/模板。它的子类可以按需要重写方法实现,但调用将以抽象类中定义的方式进行。
//创建一个抽象类,它的模板方法被设置为 final
public abstract class Game {
abstract void initialize();
abstract void startPlay();
abstract void endPlay();
//模板
public final void play(){
//初始化游戏
initialize();
//开始游戏
startPlay();
//结束游戏
endPlay();
}
}
//创建扩展了上述类的实体类
public class Cricket extends Game {
@Override
void endPlay() {
System.out.println("Cricket Game Finished!");
}
@Override
void initialize() {
System.out.println("Cricket Game Initialized! Start playing.");
}
@Override
void startPlay() {
System.out.println("Cricket Game Started. Enjoy the game!");
}
}
public class Football extends Game {
@Override
void endPlay() {
System.out.println("Football Game Finished!");
}
@Override
void initialize() {
System.out.println("Football Game Initialized! Start playing.");
}
@Override
void startPlay() {
System.out.println("Football Game Started. Enjoy the game!");
}
}
//使用 Game 的模板方法 play() 来演示游戏的定义方式
public class TemplatePatternDemo {
public static void main(String[] args) {
Game game = new Cricket();
game.play();
System.out.println();
game = new Football();
game.play();
}
}
25、访问者模式(Visitor Pattern)
使用了一个访问者类,它改变了元素类的执行算法。通过这种方式,元素的执行算法可以随着访问者改变而改变。主要将数据结构与数据操作分离。
//定义一个表示元素的接口
public interface ComputerPart {
public void accept(ComputerPartVisitor computerPartVisitor);
}
//创建扩展了上述类的实体类
public class Keyboard implements ComputerPart {
@Override
public void accept(ComputerPartVisitor computerPartVisitor) {
computerPartVisitor.visit(this);
}
}
public class Monitor implements ComputerPart {
@Override
public void accept(ComputerPartVisitor computerPartVisitor) {
computerPartVisitor.visit(this);
}
}
public class Mouse implements ComputerPart {
@Override
public void accept(ComputerPartVisitor computerPartVisitor) {
computerPartVisitor.visit(this);
}
}
public class Computer implements ComputerPart {
ComputerPart[] parts;
public Computer(){
parts = new ComputerPart[] {new Mouse(), new Keyboard(), new Monitor()};
}
@Override
public void accept(ComputerPartVisitor computerPartVisitor) {
for (int i = 0; i < parts.length; i++) {
parts[i].accept(computerPartVisitor);
}
computerPartVisitor.visit(this);
}
}
//定义一个表示访问者的接口
public interface ComputerPartVisitor {
public void visit(Computer computer);
public void visit(Mouse mouse);
public void visit(Keyboard keyboard);
public void visit(Monitor monitor);
}
//创建实现了上述类的实体访问者
public class ComputerPartDisplayVisitor implements ComputerPartVisitor {
@Override
public void visit(Computer computer) {
System.out.println("Displaying Computer.");
}
@Override
public void visit(Mouse mouse) {
System.out.println("Displaying Mouse.");
}
@Override
public void visit(Keyboard keyboard) {
System.out.println("Displaying Keyboard.");
}
@Override
public void visit(Monitor monitor) {
System.out.println("Displaying Monitor.");
}
}
//使用 ComputerPartDisplayVisitor 来显示 Computer 的组成部分
public class VisitorPatternDemo {
public static void main(String[] args) {
ComputerPart computer = new Computer();
computer.accept(new ComputerPartDisplayVisitor());
}
}