java设计模式

时间:2022-12-03 01:25:07

适配器模式

适配器就是一种适配中间件,它存在于不匹配的了两者之间,用于连接两者,使不匹配变得匹配。

手机充电需要将220V的交流电转化为手机锂电池需要的5V直流电

知识补充:手机充电器输入的电流是交流,通过变压整流输出电流是直流的。。

类适配器

️2️⃣Adaptee 源角色   :220V的交流电(家用电一般是220V)  

//家用电压
public class HomeElectri {
    //输出220v交流电,AC指的是交流电
    public int outputAC220V() {
        int output = 220;
        return output;
    }
}

1️⃣Target 目标角色 :  手机锂电池需要的5V直流电

目标类Destination,只需要定义方法,由适配器来转化:

//手机充电接口
public interface MobileCharge {
    //需要5v的直流电
    //DC指的是直流电
    int outputDC5V();
}

3️⃣Adapter 适配器角色  :手机充电器

//手机的适配器(手机充电器)
public class PhoneAdapter extends HomeElectri implements MobileCharge {

    @Override
    public int outputDC5V() {
        int output = outputAC220V();
        return (output / 44);
    }
}


对象适配器

提供一个包装类Adapter,这个包装类包装了一个Adaptee的实例,从而此包装类能够把Adaptee的API与Target类的API链接起来。


接口适配器

适配器的主要作用:把原本不兼容的接口通过适配器修改做到统一,方便调用。

实话实说,这话听着就很迷。不兼容的接口是啥意思(驴头配马嘴?)

之所以会先提到适配器,也是因为在用到GUI编程(awt,swing,swt,jface)的时候经常会遇到。

这是在编写awt编程的时候,用到了MouseAdapter,当然这块内容有很多Adapter

public class SwingDemo {
    JFrame jf = new JFrame("jframe JTable测试");
    public static void main(String[] args) {
        new SwingDemo().init();
    }

    //初始化界面(组装视图)
    public void init() {
        JButton jButton = new JButton("点我有惊喜");
        jButton.addMouseListener(new MouseAdapter() {
            @Override
            public void mouseClicked(MouseEvent e) {
                System.out.println("惊不惊喜,意不意外");
            }
        });
        jf.add(jButton);
        jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        //设置窗口大小与可见
        jf.pack();
        jf.setVisible(true);
    }
}

仔细分析一波:

addMouseListener()这个方法需要MouseListener的一个参数

public abstract class Component implements ImageObserver, MenuContainer,Serializable{
    public synchronized void addMouseListener(MouseListener l) {
        //方法体
    }

}

MouseListener是一个接口,里面有鼠标的各种事件

public interface MouseListener extends EventListener {

    public void mouseClicked(MouseEvent e);

    public void mousePressed(MouseEvent e);

    public void mouseReleased(MouseEvent e);

    public void mouseEntered(MouseEvent e);

    public void mouseExited(MouseEvent e);
}

那 MouseAdapter是怎么横空出世的呢?

MouseAdapter有2个特点

第一:它是抽象类。

第二:每个方法MouseAdapter都做了空实现,这是核心

public abstract class MouseAdapter implements MouseListener, MouseWheelListener, MouseMotionListener {

    public void mouseClicked(MouseEvent e) {}

    public void mousePressed(MouseEvent e) {}

    public void mouseReleased(MouseEvent e) {}

    public void mouseEntered(MouseEvent e) {}

    public void mouseExited(MouseEvent e) {}

    public void mouseWheelMoved(MouseWheelEvent e){}

    public void mouseDragged(MouseEvent e){}

    public void mouseMoved(MouseEvent e){}
}

上面的这种适配器用法对应的是适配器的第三种用法。。。

除此还有类适配器和对象适配器


装饰器模式

核心:在不改变原有类的基础上给类新增功能。

这是我在学习安全的并发容器类时用到过的,比如

List<Object> synchronizedList = Collections.synchronizedList(new ArrayList<>());

我们来看SynchronizedList,它是Collections的静态内部类。

public class Collections {

    static class SynchronizedList<E> extends SynchronizedCollection<E> implements List<E> {
        final List<E> list;

        SynchronizedList(List<E> list) {
            super(list);
            this.list = list;
        }

        public void add(int index, E element) {
            synchronized (mutex) {list.add(index, element);}
        }

        public E remove(int index) {
            synchronized (mutex) {return list.remove(index);}
        }
        
        //...很多方法都用synchronized代码块包裹了,做成了并发安全
    }
}