栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

设计模式01:创建型

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

设计模式01:创建型

文章目录
  • 一、单例模式
    • 1.1、饿汉式(静态常量)(可用)
    • 1.2、饿汉式(静态代码块)(可用)
    • 1.3、饿汉式(静态内部类)(推荐)
    • 1.4、懒汉式(线程不安全)(不可用)
    • 1.5、懒汉式(解决线程不安全?一)(可用但不推荐)
    • 1.6、懒汉式(解决线程不安全?二)(不可用)
    • 1.7、懒汉式(双重检查锁)(推荐)
    • 1.8、枚举(推荐)
    • 1.9、JDK源码案例
    • 1.10、注意事项
  • 二、工厂模式
    • 2.1、简单工厂模式
    • 2.2、工厂方法模式
    • 2.3、抽象工厂模式
    • 2.4、小结
  • 三、原型模式
    • 3.1、传统方式
    • 3.2、浅拷贝
    • 3.3、自定义浅拷贝
    • 3.4、深拷贝(重新Clone)
    • 3.5、深拷贝(序列化)
    • 3.6、注意事项
  • 四、建造者模式


一、单例模式 1.1、饿汉式(静态常量)(可用)

1、构造器私有化
2、类的内部创建对象
3、向外暴露一个静态的公共方法(getInstance)

public class Test01 {
    public static void main(String[] args) {
        Singleton instance1 = Singleton.getInstance();
        Singleton instance2 = Singleton.getInstance();
        System.out.println(instance1.hashCode()); // 460141958
        System.out.println(instance2.hashCode()); // 460141958
        System.out.println(instance1 == instance2);  // true
    }
}

class Singleton {
    // 1、构造器私有化,防止外部new
    private Singleton() {}

    // 2、类的内部创建对象
    private final static Singleton instance = new Singleton();

    // 3、公开静态返回该单例对象
    public static Singleton getInstance() {
        return instance;
    }
}


1.2、饿汉式(静态代码块)(可用)

推荐但是可能造成内存浪费,不过其实浪费的只有单例这个内存,还是比较可观的

class Singleton {
    private Singleton() {}
    
    private static Singleton instance;

    // 静态代码块创建单例对象
    static {
        instance = new Singleton();
    }

    public static Singleton getInstance() {
        return instance;
    }
}


1.3、饿汉式(静态内部类)(推荐)

1、当主类装载时静态内部类不会被装载
2、当调用静态内部类的方法时会导致静态内部类被装载

class Singleton {
    private Singleton() {}

    private static class SingletonInstance {
        private static final Singleton INSTANCE = new Singleton();
    }

    public static Singleton getInstance() {
        return SingletonInstance.INSTANCE;
    }
}


1.4、懒汉式(线程不安全)(不可用)
class Singleton {
    private Singleton() {}

    private static Singleton instance;

    public static Singleton getInstance() {
        if (instance == null) {
            instance = new Singleton();
        }
        return instance;
    }
}


1.5、懒汉式(解决线程不安全?一)(可用但不推荐)

解决了线程同步问题,但是每次都会进行if判断导致效率较低,可用但是不推荐

class Singleton {
    private Singleton() {}

    private static Singleton instance;

    public static synchronized Singleton getInstance() {
        if (instance == null) {
            instance = new Singleton();
        }
        return instance;
    }
}


1.6、懒汉式(解决线程不安全?二)(不可用)

不能使用如下,假如多个线程进入if判断,会导致同步后仍然创建多个对象,不能使用如下方法

class Singleton {
    private Singleton() {}

    private static Singleton instance;

    public static Singleton getInstance() {
        if (instance == null) {
            synchronized (Singleton.class) {
                instance = new Singleton();
            }
        }
        return instance;
    }
}


1.7、懒汉式(双重检查锁)(推荐)
class Singleton {
    private Singleton() {}

    private static volatile Singleton instance;

    public static Singleton getInstance() {
        // 3、以后的进入都是直接return
        if (instance == null) {
            // 1、多个线程进入此处同步
            synchronized (Singleton.class) {
                // 2、第一个进入判断为空则创建,接下来的进入则不会创建
                if (instance == null) {
                    instance = new Singleton();
                }
            }
        }
        return instance;
    }
}


1.8、枚举(推荐)
public class Test03 {
    public static void main(String[] args) {
        Singleton instance1 = Singleton.INSTANCE;
        Singleton instance2 = Singleton.INSTANCE;
        System.out.println(instance1.hashCode()); // 460141958
        System.out.println(instance2.hashCode()); // 460141958
        System.out.println(instance1 == instance2);  // true
    }
}

enum Singleton {
    INSTANCE;
}


1.9、JDK源码案例


1.10、注意事项

推荐使用:饿汉式(静态常量、静态代码块)
强烈推荐使用:懒汉式(双重检查)、饿汉式(静态内部类)、枚举


二、工厂模式 2.1、简单工厂模式

public class SimpleFactory {
    public static void main(String[] args) {
        Product p1 = Factory.createProduct("A");
        Product p2 = Factory.createProduct("B");

        p1.info();
        p2.info();
    }
}

class Factory {
    public static Product createProduct(String type) {
        Product product = null;
        switch (type) {
            case "A":
                product = new ProductA();
                break;
            case "B":
                product = new ProductB();
                break;
            // 如果每次添加新的产品都要修改此处,违反开放封闭原则    
        }
        return product;
    }
}

abstract class Product {
    public abstract void info();
}

class ProductA extends Product {

    @Override
    public void info() {
        System.out.println("产品的信息:A");
    }
}

class ProductB extends Product {

    @Override
    public void info() {
        System.out.println("产品的信息:B");
    }
}

2.2、工厂方法模式

定义一个用于创建对象的接口,让工厂决定实例化哪一个类,使类的实例化延迟到其子类

缺点:添加新产品时还需要添加对应的工厂类

public class FactoryMethod {
    public static void main(String[] args) {
        Factory factoryA = new FactoryA();
        Product productA = factoryA.createProduct();
        productA.info();

        Factory factoryB = new FactoryB();
        Product productB = factoryB.createProduct();
        productB.info();
    }
}

interface Factory {
    public Product createProduct();
}

class FactoryA implements Factory {

    @Override
    public Product createProduct() {
        return new ProductA();
    }
}

class FactoryB implements Factory {

    @Override
    public Product createProduct() {
        return new ProductB();
    }
}

interface Product {
    public void info();
}

class ProductA implements Product {

    @Override
    public void info() {
        System.out.println("产品的信息:A");
    }
}

class ProductB implements Product {

    @Override
    public void info() {
        System.out.println("产品的信息:B");
    }
}


2.3、抽象工厂模式

提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类

如果是添加新的工厂,那么代码的设计非常优秀,但如果是需要生产原先不存在的产品,如生产笔记本,那么需要更改顶层工厂接口

public class Client {
    public static void main(String[] args) {
        Factory appleFactory = new AppleFactory();
        Factory miFactory = new MiFactory();

        Pad ipad = appleFactory.createPad();
        Phone iphone = appleFactory.createPhone();
        ipad.info();
        iphone.info();

        Pad miPad = miFactory.createPad();
        Phone miPhone = miFactory.createPhone();
        miPad.info();
        miPhone.info();
    }
}

工厂接口

// 顶层工厂接口
interface Factory {
    public Pad createPad();

    public Phone createPhone();
}

入驻的工厂:每个工厂按规矩只能生产平板和手机

// 苹果工厂
class AppleFactory implements Factory {

    @Override
    public Pad createPad() {
        return new Ipad();
    }

    @Override
    public Phone createPhone() {
        return new Iphone();
    }
}

// 小米工厂
class MiFactory implements Factory {

    @Override
    public Pad createPad() {
        return new MiPad();
    }

    @Override
    public Phone createPhone() {
        return new MiPhone();
    }
}

产品接口:生产工厂对应的平板和手机

// 平板
interface Pad {
    public void info();
}

// 手机
interface Phone {
    public void info();
}

产品类

class Ipad implements Pad {

    @Override
    public void info() {
        System.out.println("产品的信息:Ipad");
    }
}

class Iphone implements Phone {

    @Override
    public void info() {
        System.out.println("产品的信息:Iphone");
    }
}

class MiPad implements Pad {

    @Override
    public void info() {
        System.out.println("产品的信息:MiPad");
    }
}

class MiPhone implements Phone {

    @Override
    public void info() {
        System.out.println("产品的信息:MiPhone");
    }
}

2.4、小结


三、原型模式


3.1、传统方式
public class Test01 {
    public static void main(String[] args) {
        Sheep parent = new Sheep("1", "a");

        Sheep s1 = new Sheep(parent.getId(), parent.getName());
        Sheep s2 = new Sheep(parent.getId(), parent.getName());
        Sheep s3 = new Sheep(parent.getId(), parent.getName());
        Sheep s4 = new Sheep(parent.getId(), parent.getName());
    }
}


3.2、浅拷贝

public class Test01 {
    public static void main(String[] args) throws CloneNotSupportedException {
        Sheep parent = new Sheep("1", "a");
        Sheep clone = (Sheep) parent.clone();
        System.out.println(parent);
        System.out.println(clone);
    }
}

class Sheep implements Cloneable {
    private String id;
    private String name;

    @Override
    protected Object clone() throws CloneNotSupportedException {
        return super.clone();
    }
}

3.3、自定义浅拷贝
public class Main {
    public static void main(String[] args) {
        Product product = new Product(2022, 189);
        Product p2 = (Product) product.clone();
        System.out.println(product);
        System.out.println(p2);
    }
}

interface Prototype {
    public Object clone();
}

class Product implements Prototype {
    private int id;
    private double price;

    @Override
    public Object clone() {
        Product product = new Product();
        product.id = this.id;
        product.price = this.price;

        return product;
    }
}

3.4、深拷贝(重新Clone)

public class Person implements Serializable, Cloneable {
    private String name;
    private Pet pet;

    @Override
    protected Object clone() throws CloneNotSupportedException {
        // 1、克隆基本类型和String类型
        Person person = (Person) super.clone();
        // 2、克隆引用类型
        person.pet = (Pet) pet.clone();
        return person;
    }
}
public class Pet implements Serializable,Cloneable {
    private String name;

    @Override
    protected Object clone() throws CloneNotSupportedException {
        return super.clone();
    }
}

3.5、深拷贝(序列化)
public Object deepClone() {
    ByteArrayOutputStream bos = null;
    ObjectOutputStream oos = null;
    ByteArrayInputStream bis = null;
    ObjectInputStream ois = null;

    try {
        // 序列化
        bos = new ByteArrayOutputStream();
        oos = new ObjectOutputStream(bos);
        oos.writeObject(this);

        // 反序列化
        bis = new ByteArrayInputStream(bos.toByteArray());
        ois = new ObjectInputStream(bis);
        Person person = (Person) ois.readObject();
        return person;
    } catch (Exception e) {
        e.printStackTrace();
        return null;
    } finally {
        try {
            bos.close();
            oos.close();
            bis.close();
            ois.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

3.6、注意事项


四、建造者模式

public class Main {
    public static void main(String[] args) {
        Director director = new Director();

        Builder1 builder1 = new Builder1();
        director.construct(builder1);
        Product p1 = builder1.getResult();
        p1.show();

        Builder2 builder2 = new Builder2();
        director.construct(builder2);
        Product p2 = builder2.getResult();
        p2.show();
    }
}

class Director {
    public void construct(Builder builder) {
        builder.buildPart();
    }
}

abstract class Builder {
    public abstract void buildPart();
    public abstract Product getResult();
}

class Builder1 extends Builder {
    Product product = new Product();

    @Override
    public void buildPart() {
        product.add("双吉堡");
        product.add("可乐");
    }

    @Override
    public Product getResult() {
        return product;
    }
}

class Builder2 extends Builder {
    Product product = new Product();

    @Override
    public void buildPart() {
        product.add("鸡肉卷");
        product.add("香芋派");
    }

    @Override
    public Product getResult() {
        return product;
    }
}

class Product {
    List parts = new ArrayList<>();

    public void add(String part) {
        parts.add(part);
    }

    public void show() {
        System.out.println("产品的组成:");
        for (String part : parts) {
            System.out.print(part + " ");
        }
        System.out.println("n");
    }
}
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/1027283.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号