【设计模式】简单理解五种设计模式

1 工厂模式

工厂模式又分为三种:简单工厂、工厂方法、抽象工厂。
快速区分:

模式概念
简单工厂不同产品实现相同接口,并且只有一个工厂类根据生产方法传入的参数创建不同的产品
工厂方法工厂不止一种,实现了相同的生产接口,不同的工厂生产对应的产品
抽象工厂工厂方法的升级,引入产品族的概念,其实就是不同工厂生产多个对应的产品

简单工厂:

abstract class P {
	void use();
}

class P1 extends P {
	void use() {...}
}

class P2 extends P {
	void use() {...}
}

class F {
	P create(int num) {
		switch (num) {
			case 1:
				return new P1();
			case 2:
				return new P2();
		}
		return null;
	}
}

工厂方法:

// 产品同上

// 工厂
abstract class F {
	P create();
}

class F1 extends F {
	P create() {
		return new P1();
	}
}

class F2 extends F {
	P create() {
		return new P2();
	}
}

抽象工厂:

// 多种产品类别,每个类别下多种产品
abstract class Phone {...}
class iPhone extends Phone {...}
class MateX extends Phone {...}

abstract class Pad {...}
class iPad extends Pad {...}
class MatePad extends Pad {...}

// 工厂
abstract class F {
	Phone producePhone();
	Pad producePad();
}
class Apple extends F {
	Phone producePhone() {
		return new iPhone();
	}
	Pad producePad() {
		return new iPad();
	}
}
class Huawei extends F {
	Phone producePhone() {
		return new MateX();
	}
	Pad producePad() {
		return new MatePad();
	}
}

2 单例模式

单例模式又分为懒汉式和饿汉式。
快速区分:

模式概念
饿汉式类加载时就已经创建好了唯一实例
懒汉式调用获取实例方法时才会创建

对于普通的单例模式写法(即不使用静态内部类和枚举类),根据类加载机制,如果单例类还没有进行初始化(没调用过静态方法,没获取过非final的基本类型静态成员变量),饿汉式和懒汉式其实本质没什么不同。

比如下面这段饿汉式代码:

    final static Product product = new Product();
    private Product() {
        System.out.println("A product has been created.");
    }
    static Product getInstance() {
        return product;
    } }

class Main {
    public static void main(String[] args) {
        System.out.println("=====main=====");
        System.out.println(Product.getInstance());
    } } 

Product的单例依然会在调用getInstance时才会创建,并且这个创建的线程安全由JVM保障。

而且单例模式的所有写法都是可以用一些奇怪的方式破坏的。可以用反射修改,即使是枚举类也可以用Unsafe来修改。

3 装饰者模式

套娃模式,比如JDK中的IO流使用了这种模式。

// 商品
abstract class Meal {
	int cost();
}
class SimpleMeal extends Meal {
	int cost() {
		return 10;
	}
}
class Takeaway extends Meal {
	Meal Meal;
	Takeaway(Meal meal) {
		this.meal = meal;
	}
	int cost() {
		return meal.cost() + 5;
	}
}

4 代理模式

代理模式又分为静态代理和动态代理。
快速区分:

模式概念
静态代理通常只代理一个类
动态代理代理一个接口下的多个实现类

静态代理:

interface IssueTickets {
	void countDown();
}
// 票仓放票
class TicketBunker implements IssueTickets {
	int ticketLeft = 10;
	public void countDown() {
		ticketLeft--;
	}
}
// 火车站代理售票
class TrainStation implements IssueTickets {
	TicketBunker bunker = new TicketBunker();
	public void countDown() {
		if (bunker.ticketLeft > 0) {
			bunker.countDown();
		}
	}
}

动态代理主要就是用JDK动态代理(通过接口)和CGLIB动态代理(通过继承)。

代理模式和装饰者模式有点像,主要区别还是在于目的:
代理模式重在控制(权限检查,日志记录等),装饰者模式重在增强(增加新的行为等)。

5 观察者模式

订阅发布模式。回调函数就是一种订阅者只有一个的观察者模式。

// 被订阅接口
interface Subject {
	// 添加观察者
    void addObserver(Observer o);
    // 删除观察者
    void removeObserver(Observer o);
    // 通知所有观察者
    void notifyObservers();
}
// 订阅者接口
interface Observer {
    // 更新方法,接收被观察者的状态变化
    public void update(String message);
}
// up主
class Up implements Subject {
	// 订阅者
	Set<Observer> observers = new HashSet<>();
	// 最新信息
	String message;

	void up(String message) {
		this.message = message;
		notifyObservers();
	}
	void addObserver(Observer o) {
		observers.add(o);
	}
    void removeObserver(Observer o) {
		observers.remove(o);
	}
    void notifyObservers() {
		for (Observer o : observers) {
			o.update(message);
		}
	}
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值