zoukankan      html  css  js  c++  java
  • java多线程(二)——用到的设计模式

    接上篇:java多线程(一)http://www.cnblogs.com/ChaosJu/p/4528895.html

    java实现多线程的方式二,实现Runable接口用到设计模式——静态代理模式

    一.代理模式

    • 代理模式的定义

      代理模式(Proxy Pattern)是对象的结构型模式,代理模式给某一个对象提供了一个代理对象,并由代理对象控制对原对象的引用。

      代理模式不会改变原来的接口和行为,只是转由代理干某件事,代理可以控制原来的目标,例如:代理商,代理商只会卖东西,但并不会改变行为,不会制造东西。

    • 代理模式涉及到的角色

    1. 抽象角色:声明真实对象和代理对象的共同接口;
    2. 代理角色:代理对象角色内部含有对真实对象的引用,从而可以操作真实对象,同时代理对象提供与真实对象相同的接口以便在任何时刻都能替代真实对象相同的接口以便在任何时刻都能替代真实对象。同时,代理对象可以再执行真实对象操作时,附加其他的操作,相当于对象真实对象进行封装;
    3. 真实角色:代理角色代表的真实对象,是我们最终要应用的对象。
    • 代理模式的类结构图

    二、静态代理

    •   代理模式举例

         楼主我要结婚,但是怕麻烦,所以找婚庆公司帮忙布置洞房、搭场景、主持婚礼,大家要清楚真正结婚的是我不是婚庆公司,我们的共同的目的就是结婚顺利,

         其实就是我结婚找婚庆公司帮忙,婚庆公司帮我完婚,并且加了很多修饰。

         角色分析:

         真实角色:楼主

         代理角色:婚庆公司

         抽象角色(共同的接口): 结婚

    /**
     * 静态代理 设计模式
     * 1、真实角色
     * 2、代理角色: 持有真实角色的引用
     * 3、二者 实现相同的接口
     * 
     * @author chaosju
     *
     */
    public class StaticProxy {
    
        public static void main(String[] args) {
            //创建真实角色
            Marry you =new LouZhu();
            //创建代理角色 +真实角色的引用
            Marry company =new WeddingCompany(you);
            //执行任务
            company.marry();
        }
    
    }
    //接口
    interface Marry{
        public abstract void marry();
    }
    //真实角色
    class LouZhu implements Marry{
    
        @Override
        public void marry() {
            System.out.println("LouZhu and  嫦娥结婚了....");
        }
        
    }
    //代理角色
    class WeddingCompany implements Marry{
        private Marry louzhu;
        public WeddingCompany() {
        }
        
        public WeddingCompany(Marry louzhu) {
            this.louzhu = louzhu;
        }
        private void before(){
            System.out.println("布置洞房....");
            
        }
        private void after(){
            System.out.println("闹洞房....");
        }
    @Override
    public void marry() { before(); louzhu.marry(); after(); } }

    执行结果:

    缺点:

    1)代理类和委托类实现了相同的接口,代理类通过委托类实现了相同的方法。这样就出现了大量的代码重复。如果接口增加一个方法,除了所有实现类需要实现这个方法外,所有代理类也需要实现此方法。增加了代码维护的复杂度。

    2)代理对象只服务于一种类型的对象,如果要服务多类型的对象。势必要为每一种对象都进行代理,静态代理在程序规模稍大时就无法胜任了。

    举例说明:代理可以对实现类进行统一的管理,如在调用具体实现类之前,需要打印日志等信息,这样我们只需要添加一个代理类,在代理类中添加打印日志的功能,然后调用实现类,这样就避免了修改具体实现类。满足我们所说的开闭原则。但是如果想让每个实现类都添加打印日志的功能的话,就需要添加多个代理类,以及代理类中各个方法都需要添加打印日志功能(如上的代理方法中删除,修改,以及查询都需要添加上打印日志的功能)。

    即静态代理类只能为特定的接口(Service)服务。如想要为多个接口服务则需要建立很多个代理类。则需要引入动态代理。

    •   静态代理模式在java多线程实现Runable接口方式中的应用

    • //实现runnable接口的线程类
      public class Programmer implements Runnable {
      
          public void run() {
              for(int i=0;i<1000;i++){
                  System.out.println("一边敲helloworld....");
              }
          }
      
      
      }
      
      public class ProgrammerApp {
      
          public static void main(String[] args) {
               //1)、创建真实角色
              Programmer pro =new Programmer();        
                //2)、创建代理角色 +真实角色引用
              Thread proxy =new Thread(pro);
                //3)、调用 .start() 启动线程
              proxy.start();
          
          }
      
      }

      为什么上述的方式实现静态代理?

    • Thread和programer都实现了Runnable接口
    • Thread作为代理角色----持有真实角色引用
    • Programer是真实角色
    采菊东篱下,悠闲现南山~
  • 相关阅读:
    Java MVC和三层架构
    EL表达式
    EL表达式中的11个隐式对象
    JDBC连接数据库7个步骤
    JSP九大内置对象和四个作用域
    Eclipse常用快捷键大全
    Java的绝对路径和相对路径
    Servlet中相对路径与绝对路径
    mysql8的深坑
    mysql单列索引和联合索引
  • 原文地址:https://www.cnblogs.com/ChaosJu/p/4531795.html
Copyright © 2011-2022 走看看