《设计模式——java版》(二)

来源:互联网 发布:友邦群发软件 垃圾 编辑:程序博客网 时间:2024/04/30 22:28

第三章  创建型模式简介

一、单例模式 

         1. 意思是:确保一个类只有一个实例,而且自行实例化并向整个系统提供这个实例

         2. 适用场景:建立目录、数据库连接等需要单线程操作的场合,用于实现对系统资源的控制。

         3.分类:饿汉式:类加载的时候就进行对象实例化
                       懒汉式:第一次引用类时,才进行对象实例化

                    3.1饿汉式(线程安全)

public class Singleton {//1. 构造方法私有化,外部就无法创建多个实例***重要private Singleton(){}//2. 创建类的唯一实例,用static来修饰,可以直接用类名来获取实例private static Singleton instance = new Singleton();//3. 提供一个获取实例的方法public static Singleton getInstance(){return instance;}}
                         由于构造函数是私有的,因此不能被继承。

                     3.2懒汉式(线程不安全)

public class Singleton {//1.构造方法私有化private Singleton(){}//2.声明类的实例private static Singleton instance;//3.使用实例的方法public static Singleton getInstance(){if (instance == null) {instance = new Singleton();}return instance;}}

                      3.3懒汉式(线程安全)

public class Singleton2 {//1.构造函数私有化private Singleton2(){}//2.声明类的实例private static Singleton2 instance;//3.获取一个获得实例的方法public static synchronized Singleton2 getInstance(){if (instance == null) {instance = new Singleton2();}for (int i = 0; i < 10; i++) {System.out.println(i);}return instance;}}


            4.饿汉式和懒汉式的区别

                    (1)饿汉式在类加载时就被实例化,懒汉式是在类第一被引用时实例化
                    (2)从资源利用效率上说,饿汉式要差一些;但从速度和反应时间角度来讲,饿汉式单例类则比懒汉式单例类稍好些

            5.单例模式的优缺点

                     优点:
                              (1)减少内存的开支,特别是一个对象需要频繁的创建、销毁时
                              (2)由于单例模式只生成一个实例,减少了系统的性能开销,当一个对象的产生需要比较多资源时,如读取配置文件、产生其他依赖对象时,则可以通过                                           在启用时直接产生一个对象,然后用永久驻留内存的方式来解决
                              (3)单例模式可以避免对资源的多重占用,例如一个写文件动作,由于只有一个实例存在于内存中,避免了对同一资源文件的同时操作
                              (4)单例模式可以在系统设置全局的访问点,优化和共享资源访问,例如,可以设计一个单例类,负责所有数据表的映射处理
                     缺点:
                              (1)单例模式无法创建子类,扩展困难
                              (2)单例模式对测试不利
                              (3)单例模式与单一职责原则有冲突

             6.适用场景

                          (1)要求生成唯一序列号的场景
                          (2)在整个项目中需要一个共享访问点或共享数据.例如:一个Web页面上的计数器,可以不用每次刷新都记录到数据库中,使用单例模式保持计数器的值,                                       并确保是线程安全的
                          (3)创建一个对象需要消耗的资源过多,如访问IO或数据库等资源等
                          (4)需要定义大量的静态常量和静态方法的环境

             7.应用

                          Spring框架中的每个Bean默认就是单例的;Java基础类库中的java.lang.Runtime类也采用了单例模式,其getRuntime()方法返回了唯一的实例
/*Created By guolujie 2017年10月16日*/class NumThread extends Thread{private String threadName;public NumThread(String name){threadName = name;}@Overridepublic void run() {// TODO Auto-generated method stubSingleton thread1 = Singleton.getInstance();for (int i = 0; i < 5; i++) {System.out.println(threadName + "第" + thread1.getNum() + "次访问!");try {this.sleep(1000);} catch (Exception e) {// TODO: handle exceptione.printStackTrace();}}}}public class test {public static void main(String[] args) {NumThread numThread1 = new NumThread("线程A");NumThread numThread2 = new NumThread("线程B");numThread1.start();numThread2.start();}}

                              运行结果:
                                                      

二、工厂方法模式

             1.工厂方法模式又叫虚拟构造函数模式或者多态性工厂模式。工厂方法模式的用意是,定义一个创建产品对                    象的工厂接口,将实际创建性工作推迟到子类中。

             2.在工厂方法模式中共涉及以下四个角色:

                    (1)抽象工厂角色:该角色是工厂方法模式的核心,与应用系统无关,任何在创建对象的工厂类必须实现这个接口
                    (2)具体工厂角色:该角色实现了抽象工厂接口,含有与应用密切相关的逻辑,并且受到应用程序的调用以创建产品对象
                    (3)抽象产品角色:该角色负责定义产品的共性,实现对产品最抽象的定义
                    (4)具体产品角色:该角色实现抽象产品角色所声明的接口,工厂方法模式所创建的每一个对象都是某个具体产品角色的实例

             3.抽象工厂代码实例

                           3-1抽象工厂Creator.java

public interface Creator {/* * 工厂方法 * 创建一个产品对象,其输入参数类型可以自行设置 */public <T extends Product> T factory(Class<T> c);}

                           3-2抽象产品Produce.java

public interface Product {//产品类的公共方法public void method1();public void method2();}

                          3-3具体工厂类ConcreteCreator.java

public class ConcreteCreator implements Creator {public <T extends Product> T factory(Class<T> c){Product product = null;try {product = (Product) Class.forName(c.getName()).newInstance();} catch (Exception e) {// TODO: handle exception}return (T) product;}}

                          3-4具体产品类ConcreteProduct.java

public class ConcreteProduct implements Product {public void method1(){//业务逻辑处理代码}public void method2(){//业务逻辑处理代码}}

                         3-5应用代码FactoryMethodDemo.java

public class FactoryMethodDemo {public static void main(String[] args) {// TODO Auto-generated method stubCreator creator = new ConcreteCreator();Product product = creator.factory(ConcreteProduct.class);/* * 继续业务处理 */}}



            4.工厂方法模式的优点

                             优点:(1)良好的封装性,代码结构清晰
                                        (2)优秀的可扩展性
                                        (3)屏蔽产品类
                                        (4)工厂方法模式是典型的解耦框架

            5.工厂方法模式的适用场景

                              (1)工厂方法模式是new一个对象的替代品,因此在所有需要生成对象的地方都可以使用,会增加代码的复杂度
                              (2)需要灵活的可扩展的框架时,可以考虑采用工厂方法模式
                              (3)工厂方法模式可以用到异构项目中
                              (4)工厂方法模式可以使用在测试驱动开发的框架下

            6.工厂方法模式的实例

                        
public interface FruitGardener {public Fruit factory();}                 
public interface Fruit {public void grow();}
                  
public class AppleGardener implements FruitGardener {public Fruit factory(){return new Apple();}}

public class GrapeGardener implements FruitGardener {public Fruit factory(){return new Grape();}}

public class Apple implements Fruit {private int treeAge;public int getTreeAge() {return treeAge;}public void setTreeAge(int treeAge) {this.treeAge = treeAge;}public void grow(){System.out.println("苹果正在生长...");}public void harvest(){System.out.println("收获苹果");}public void plant(){System.out.println("栽种苹果");}}
public class Grape implements Fruit {private boolean seedless;public boolean isSeedless() {return seedless;}public void setSeedless(boolean seedless) {this.seedless = seedless;}public void grow(){System.out.println("葡萄正在生长...");}public void harvest(){System.out.println("收获葡萄");}public void plant(){System.out.println("栽种葡萄");}}

public class ClientDemo {public static void main(String[] args) {// TODO Auto-generated method stubFruitGardener fruitGardener = new AppleGardener();Apple apple = (Apple) fruitGardener.factory();apple.plant();apple.grow();apple.harvest();fruitGardener = new GrapeGardener();Grape grape = (Grape) fruitGardener.factory();grape.plant();grape.grow();grape.harvest();}}


    


原创粉丝点击