美文网首页
创建型模式(二):建造者,原型,单例模式

创建型模式(二):建造者,原型,单例模式

作者: JBryan | 来源:发表于2020-03-04 11:49 被阅读0次
4.建造者模式

建造者模式和抽象工厂模式很相似,如果抽象工厂模式时一个汽车配件生产厂,那么建造者模式就是一个汽车组装厂,通过对配件的组装,返回一台完整的汽车。
4.1.实例说明
某游戏软件中人物角色包括多种不同类型,不同类型的人物角色,其性别,脸型,服装,发型等外部特性都有差异,使用建造者模式创建人物角色对象。
4.2.实例类图

建造者.jpg
4.3.实例代码
package com.ljessie.designpattern.creational.builder;

public class Actor {
    private String type;
    private String sex;
    private String face;
    private String costume;
    private String hairStyle;

    public String getType() {
        return type;
    }

    public void setType(String type) {
        this.type = type;
    }

    public String getSex() {
        return sex;
    }

    public void setSex(String sex) {
        this.sex = sex;
    }

    public String getFace() {
        return face;
    }

    public void setFace(String face) {
        this.face = face;
    }

    public String getCostume() {
        return costume;
    }

    public void setCostume(String costume) {
        this.costume = costume;
    }

    public String getHairStyle() {
        return hairStyle;
    }

    public void setHairStyle(String hairStyle) {
        this.hairStyle = hairStyle;
    }
}
package com.ljessie.designpattern.creational.builder;

public abstract class ActorBuilder {
    protected Actor actor = new Actor();
    public abstract void buildType();
    public abstract void buildSex();
    public abstract void buildFace();
    public abstract void buildcostume();
    public abstract void buildHairStyle();

    public Actor createActor(){
        return actor;
    }
}
package com.ljessie.designpattern.creational.builder;

public class HeroBuilder extends ActorBuilder {
    @Override
    public void buildType() {
        actor.setType("英雄");
    }

    @Override
    public void buildSex() {
        actor.setSex("男");
    }

    @Override
    public void buildFace() {
        actor.setFace("英俊");
    }

    @Override
    public void buildcostume() {
        actor.setCostume("盔甲");
    }

    @Override
    public void buildHairStyle() {
        actor.setHairStyle("飘逸");
    }
}
package com.ljessie.designpattern.creational.builder;

public class AngelBuilder extends ActorBuilder {
    @Override
    public void buildType() {
        actor.setType("天使");
    }

    @Override
    public void buildSex() {
        actor.setSex("女");
    }

    @Override
    public void buildFace() {
        actor.setFace("漂亮");
    }

    @Override
    public void buildcostume() {
        actor.setCostume("白裙");
    }

    @Override
    public void buildHairStyle() {
        actor.setHairStyle("齐腰长发");
    }
}
package com.ljessie.designpattern.creational.builder;

public class ActorController {
    public Actor construct(ActorBuilder builder){
        builder.buildSex();
        builder.buildcostume();
        builder.buildFace();
        builder.buildHairStyle();
        builder.buildType();
        return builder.createActor();
    }
}
package com.ljessie.designpattern.creational.builder;

public class Test {
    public static void main(String[] args) {
        ActorController controller = new ActorController();
        ActorBuilder builder = new HeroBuilder();
        Actor actor = controller.construct(builder);
        System.out.println("type:"+actor.getType());
        System.out.println("sex:"+actor.getSex());
        System.out.println("costume:"+actor.getCostume());
        System.out.println("face:"+actor.getFace());
        System.out.println("hairType:"+actor.getHairStyle());
    }
}

运行结果:

type:英雄
sex:男
costume:盔甲
face:英俊
hairType:飘逸

工厂模式是用来创建不同但是相关类型的对象(继承同一父类或者接口的一组子类),由给定的参数来决定创建哪种类型的对象。建造者模式是用来创建一种类型的复杂对象,通过设置不同的可选参数,“定制化”地创建不同的对象。
网上有一个经典的例子很好地解释了两者的区别。顾客走进一家餐馆点餐,我们利用工厂模式,根据用户不同的选择,来制作不同的食物,比如披萨、汉堡、沙拉。对于披萨来说,用户又有各种配料可以定制,比如奶酪、西红柿、起司,我们通过建造者模式根据用户选择的不同配料来制作披萨。

5.原型模式

5.1.实例说明
在某OA系统中,用户可以创建工作周报,由于某些岗位每周工作存在重复性,因此可以通过复制原有工作周报,并进行局部修改来快速新建工作周报。现使用原型模式来实现该功能。
5.2.实例类图

原型模式.jpg
5.3.实例代码
package com.ljessie.designpattern.creational.prototype;

public class WeeklyLog implements Cloneable {
    private String name;
    private String date;
    private String content;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getDate() {
        return date;
    }

    public void setDate(String date) {
        this.date = date;
    }

    public String getContent() {
        return content;
    }

    public void setContent(String content) {
        this.content = content;
    }

    public Object clone(){
        try {
            Object obj = super.clone();
            return obj;
        } catch (CloneNotSupportedException e) {
            e.printStackTrace();
            return null;
        }
    }

}
package com.ljessie.designpattern.creational.prototype;

public class Test {
    public static void main(String[] args) {
        WeeklyLog log_previous = new WeeklyLog();
        log_previous.setName("张三");
        log_previous.setDate("第12周");
        log_previous.setContent("每天加班");
        System.out.println(log_previous.getName());
        System.out.println(log_previous.getDate());
        System.out.println(log_previous.getContent());
        System.out.println("---------------------------");
        WeeklyLog log_current = (WeeklyLog) log_previous.clone();
        log_current.setDate("第13周");
        System.out.println(log_current.getName());
        System.out.println(log_current.getDate());
        System.out.println(log_current.getContent());
    }
}

运行结果:

张三
第12周
每天加班
---------------------------
张三
第13周
每天加班

原型模式有两种实现方法,深拷贝和浅拷贝。浅拷贝只会复制对象中基本数据类型数据和引用对象的内存地址,不会递归地复制引用对象,以及引用对象的引用对象……而深拷贝得到的是一份完完全全独立的对象。所以,深拷贝比起浅拷贝来说,更加耗时,更加耗内存空间。
深拷贝实现:先将对象序列化,然后再反序列化成新的对象。对象要实现Serializable接口

public Object deepCopy(Object object){
        ByteArrayOutputStream bo = new ByteArrayOutputStream();
        ObjectOutputStream oo = null;
        Object result = null;
        try {
            oo = new ObjectOutputStream(bo);
            oo.writeObject(object);
            ByteArrayInputStream bi = new ByteArrayInputStream(bo.toByteArray());
            ObjectInputStream oi = new ObjectInputStream(bi);
             result= oi.readObject();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
        return result;
    }
6.单例模式

单例设计模式(Singleton Design Pattern)理解起来非常简单。一个类只允许创建一个对象(或者实例),那这个类就是一个单例类,这种设计模式就叫作单例设计模式,简称单例模式。
6.1懒加载: 在需要的时候,才会进行实例化。

package com.ljessie.designpattern.creational.singleton;

/**
 * 懒汉式单例
 * 在需要的时候,才会进行实例化
 * @author zbw
 *
 */
public class LazySingleton {
    
    //volatile防止JVM指令重排序
    private static volatile LazySingleton lazySingleton = null;
    
    private LazySingleton() {
        
    }
    
    /**
     * 非线性安全的,加上synchronized
     * 若加到方法上,太消耗性能
     * @return
     */
    public static LazySingleton getInstance() {
        if(lazySingleton == null) {
            synchronized (LazySingleton.class) {
                if(lazySingleton == null) {
                    lazySingleton = new LazySingleton();
                }
            }
        }
        return lazySingleton;
    }
    
    public static void main(String[] args) {
        for (int i = 0; i < 10; i++) {
            new Thread() {
                @Override
                public void run() {
                    System.out.println(LazySingleton.getInstance());
                }
            }.start();
        }
    }
    
}

6.2饿汉:在类加载的时候,就已经实例化。

package com.ljessie.designpattern.creational.singleton;

/**
 * 饿汉式单例,在类加载的时候,就已经实例化。
 * @author zbw
 *
 */
public class HungerSingleton {
    
    
    private static HungerSingleton hungerSingleton = new HungerSingleton();
    
    public static HungerSingleton getInstance() {
        return hungerSingleton;
    }
    
    private HungerSingleton() {
        
    }
    
    public static void main(String[] args) {
        for (int i = 0; i < 10; i++) {
            new Thread() {
                @Override
                public void run() {
                    System.out.println(HungerSingleton.getInstance());
                }
            }.start();
        }
    }

}

相关文章

  • PHP常用设计模式

    # 创建型 单例模式 工厂模式 工厂抽象模式 原型模式 建造者模式 # 结构型 # 行为型 # 3.注册模式 # ...

  • 设计模式之创建型

    创建型指的是对象模型的创建。 有以下五种方式: 单例、原型、工厂、抽象工厂、建造者。 单例有懒汉模式和饿汉模式,区...

  • 23种设计模式

    创建型 工厂模式 ( 工厂方法模式, 抽象工厂模式, 建造者模式 ) 单例模式 原型模式 结构型 适配器模式 装饰...

  • 设计模式

    设计模式分为 3 大类型共 23 种:创建型:工厂方法模式、抽象工厂模式、单例模式、建造者模式、原型模式。结构型:...

  • 简单工厂模式

    创建型设计模式: 简单工厂模式、工厂方法模式、抽象工厂模式、单例模式、原型模式和建造者模式。 统共六种。 本此分享...

  • 前篇

    一、常见的设计模式? 创建型:工厂方法模式、抽象工厂模式、建造者模式、原型模式、单例模式 结构型:适配器模式、桥接...

  • 目录(持续更新)

    一、创建性模式(对象模式) 创建性模式-工厂创建性模式-建造者模式创建性模式-单例模式&多例模式创建性模式-原型模...

  • 2021-11-16 - 学习记录

    设计模式学习:创建型:工厂(工厂方法,抽象工厂),建造者,单例,原型 设计模式:工厂模式 简单工厂 工厂方法 抽象工厂

  • 设计模式的分类

    一、创建型模式单例 工厂 抽象工厂 建造者(Builder) 原型二、结构型模式适配器 ...

  • JavaScript设计模式

    设计模式分类(23种设计模式) 创建型单例模式原型模式工厂模式抽象工厂模式建造者模式 结构型适配器模式装饰器模式代...

网友评论

      本文标题:创建型模式(二):建造者,原型,单例模式

      本文链接:https://www.haomeiwen.com/subject/malplhtx.html