一篇文章搞懂主流设计模式
1 创建形模式
1.1 单例模式
/**
* 主要应用场景:
* 因单例模式的优点,可以确保一个类只有一个实例,不用重复实例化类,大大节约时间
* 通常在资源访问,连接,资源池控制等情况下来进行使用
*/
public class SingleDemo {
public static SingleDemo instance;
SingleDemo(){
}
public static synchronized SingleDemo getInstance(){
if(instance == null){
instance = new SingleDemo();
}
return instance;
}
public void connect(){
System.out.println("连接操作");
}
}
# main函数
SingleDemo singleDemo = SingleDemo.getInstance();
singleDemo.connect();
1.2 工厂模式
*** 工厂模式是用来通过一个类,实例化不同的类,可以十分便捷的添加新的业务逻辑 **
例:目前有个零件加工厂,大家只需要知道是加工零件的。不需要担心加工哪个公司的零件,无论哪个公司的零件,到工厂内部,全部按照内部的操作来走。这样就免去了再修改业务逻辑代码的麻烦。各个业务逻辑各司其职,有效的开发项目进度。
//以下用对接各种电商平台为例
/**
* 规定接口类
*/
public interface GoodsHandleImp {
public List<Goods> searchGoodsList();
}
public class Jingdong implements GoodsHandleImp {
@Override
public List<Goods> searchGoodsList() {
System.out.println("这个是京东的数据");
return null;
}
}
public class Pinduoduo implements GoodsHandleImp{
@Override
public List<Goods> searchGoodsList() {
System.out.println("这个是拼多多的数据");
return null;
}
}
public class Tao implements GoodsHandleImp{
@Override
public List<Goods> searchGoodsList() {
System.out.println("这个是淘宝的数据");
return null;
}
}
//工厂类
public class FactoryDemo {
public Set<String> platforms = new HashSet<String>();
FactoryDemo(){
platforms.add("Jingdong");
platforms.add("Pinduoduo");
platforms.add("Tao");
}
public GoodsHandleImp initGoodsHandle(String platform){
if(platform == null){
System.out.println("Not found platform");
return null;
}
if(!platforms.contains(platform)){
System.out.println("Not found platform");
return null;
}
GoodsHandleImp goodsHandleImp = null;
switch (platform){
case "Jingdong":
goodsHandleImp = new Jingdong();
break;
case "Pinduoduo":
goodsHandleImp = new Pinduoduo();
break;
case "Tao":
goodsHandleImp = new Tao();
break;
}
return goodsHandleImp;
}
}
//main函数
public static void main(String[] args) {
FactoryDemo factory = new FactoryDemo();
GoodsHandleImp handle = factory.initGoodsHandle("Tao");
handle.searchGoodsList();
}
1.3 抽象工厂类
现在用一张图来进行说明一下该抽象工厂类与工厂类的区别在哪。这个是抽象工厂类的例子。对于普通工厂类来讲,普通工厂类只能满足单一的需求,譬如
工厂类情况下:
所有的食品加工厂操作,只能在一个类中去实现。大大增加了代码的冗余层度,为后续开发来讲照成损失,并且多人合作麻烦。
抽象工厂类下:
可以将不同的操作,转换成单独的类来进行实例化。可以让程序员专注的注重自己应该做的业务逻辑。
以下代码仅用食物处理功能来进行做例子
//食物处理操作类
public interface HandleFoods {
void chicken();
void pig();
void bird();
}
//食物处理实现类
public class ElmHandleFoods implements HandleFoods {
@Override
public void chicken() {
System.out.println("这里是饿了么在处理鸡肉");
}
@Override
public void pig() {
System.out.println("这里是饿了么在处理猪肉");
}
@Override
public void bird() {
System.out.println("这里是饿了么在处理鸽子肉");
}
}
public class MeituanHandleFoods implements HandleFoods {
@Override
public void chicken() {
System.out.println("这里是美团在处理鸡肉");
}
@Override
public void pig() {
System.out.println("这里是美团在处理猪肉");
}
@Override
public void bird() {
System.out.println("这里是美团在处理鸽子肉");
}
}
//工厂操作类
public interface AbcFactory {
HandleFoods createHandleFoodsClass();
}
//实际工厂类
public class ElmFactory implements AbcFactory{
@Override
public HandleFoods createHandleFoodsClass() {
return new ElmHandleFoods();
}
}
public class MeituanFacotry implements AbcFactory{
@Override
public HandleFoods createHandleFoodsClass() {
return new MeituanHandleFoods();
}
}
//main函数,用来实现启动饿了么来处理鸡肉的功能。
public static void main(String[] args) {
AbcFactory factory = new ElmFactory();
HandleFoods handleFoods = factory.createHandleFoodsClass();
handleFoods.chicken();
}
通过以上代码,就可以快速的实现一个大型系统的代码架构需求。更快速的让每个事情做自己该做的事。为以后的开发打下基石
2 结构模式
2.1 适配器模式
允许对象间的接口不兼容问题通过一个转换接口解决。
例:
有个商品搜索的功能,老平台适用,但是新的平台不适用。那么就需要写一个适配器来解决该问题。
//老平台
public class OldPlatform implements Platform{
@Override
public void searchGoods() {
System.out.println("old platform");
}
}
//新平台
public class NewPlatform {
public void searchGoods(){
System.out.println("新的平台");
}
}
//适配器
public class AdaptNewPlatform implements Platform{
@AutoWrite
NewPlatform newPlatform;
@Override
public void searchGoods() {
newPlatform.searchGoods();
}
}
2.2 装饰器模式
装饰器模式,很明显,就是把原本不属于该类的操作,给该类添加新的功能。
利用给蛋炒饭加一份香肠为例
//炒饭类
public interface FiredRiceInterface {
void cost();
}
//炒饭实现类
public class FiredRice implements FiredRiceInterface{
@Override
public void cost() {
System.out.println("普通蛋炒饭");
}
}
//炒饭装饰接口类
public interface FiredRiceBase extends FiredRiceInterface{
FiredRiceInterface getFiredRice();
}
//炒饭装饰实现类
public class RiceOthers implements FiredRiceBase{
FiredRiceInterface firedRice;
public RiceOthers(FiredRiceInterface firedRiceInterface){
this.firedRice = firedRiceInterface;
}
@Override
public FiredRiceInterface getFiredRice() {
return firedRice;
}
@Override
public void cost() {
firedRice.cost();
System.out.println("加了一份香肠");
}
}
//main函数
FiredRiceInterface firedrice = new FiredRice();
FiredRiceInterface firedOthers = new RiceOthers(firedrice);
firedOthers.cost();
自我认为代理操作和装饰器很相似,但是省去了一些复杂的步骤,可以直接在不改变原代码的情况下,增加新的功能模块。
譬如。
代理模式是一种结构型设计模式,它为另一个对象提供一个代替或占位符,以控制对它的访问。代理可以在客户端和目标对象之间起到中介的作用,并且可以在不改变目标对象的代码前提下,增加额外的功能操作,比如延迟初始化、访问控制、日志记录等。
代理模式的Java实现示例
假设我们有一个Image
类,加载图片时需要一些时间。我们希望在图片加载完成之前显示一个加载指示器,以提高用户体验。
首先定义Image
接口:
interface Image {
void display();
}
然后实现具体的Image
类:
class RealImage implements Image {
private String fileName;
public RealImage(String fileName) {
this.fileName = fileName;
}
public void display() {
System.out.println("Displaying " + fileName);
// 假设加载图片需要一些时间
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
接下来,定义代理类:
class ImageProxy implements Image {
private RealImage realImage;
private String fileName;
public ImageProxy(String fileName) {
this.fileName = fileName;
}
public void display() {
if (realImage == null) {
realImage = new RealImage(fileName);
}
realImage.display();
}
}
客户端代码:
public class Client {
public static void main(String[] args) {
Image image = new ImageProxy("example.jpg");
image.display();
}
}
3 行为模式
3.1策略模式
策略模式可以创建不同的策略,用来解决不同的问题。也就是说,都是同样执行方法,但是执行的算法是不同的。
譬如
//基础策略
public interface BaseStrategy {
int execute(int a,int b);
}
//算法策略实现类
public class RandomStrategy implements BaseStrategy{
@Override
public int execute(int a, int b) {
return 3;
}
}
public class QuicklyStrategy implements BaseStrategy{
@Override
public int execute(int a, int b) {
return 2;
}
}
//策略使用类
public class ExecuteStrategy {
BaseStrategy strategy;
public ExecuteStrategy(BaseStrategy strategy){
this.strategy = strategy;
}
public void setStrategy(BaseStrategy strategy){
this.strategy = strategy;
}
public int execute(int a,int b){
return strategy.execute(a,b);
};
}
//main函数
public static void main(String[] args) {
ExecuteStrategy executeStrategy = new ExecuteStrategy(new RandomStrategy());
System.out.println(executeStrategy.execute(1,2));
executeStrategy.setStrategy(new QuicklyStrategy());
System.out.println(executeStrategy.execute(1,2));
}
这样就可以保证想使用哪个算法的时候,就可以直接使用了。
** 以上这些是我在工作和程序设计中常用到的设计模式,而设计模式不仅仅只有这些,还有命令模式,观察者模式等操作。我认为这些模式都是由以上模式衍生出来的,最重要的还是这些。掌握这些设计模式,可以对程序更好的设计。一个好的coder,不仅仅要有聪明的脑袋,更要勤奋。我们一起加油吧! **