Rumah Java javaTutorial Java使用设计模式中的代理模式构建项目的实例展示

Java使用设计模式中的代理模式构建项目的实例展示

Feb 07, 2017 pm 01:26 PM

概念

代理模式(Proxy):代理模式其实就是多一个代理类出来,替原对象进行一些操作。比如咱有的时候打官司需要请律师,因为律师在法律方面有专长,可以替咱进行操作表达咱的想法,这就是代理的意思。代理模式分为两类:1、静态代理(不使用jdk里面的方法);2、动态代理(使用jdk里面的InvocationHandler和Proxy)。
静态代理由程序员创建或工具生成代理类的源码,再编译代理类。所谓静态也就是在程序运行前就已经存在代理类的字节码文件,代理类和委托类的关系在运行前就确定了。 
动态代理类的源码是在程序运行期间由JVM根据反射等机制动态的生成,所以不存在代理类的字节码文件。代理类和委托类的关系是在程序运行时确定。

示例
这里我们举一个静态代理的例子:
类图:

Java使用设计模式中的代理模式构建项目的实例展示

/** 
 * 游戏者接口 
 * 
 */
public interface IGamePlayer { 
  
  // 登录游戏 
  public void login(String user, String password); 
  
  // 杀怪,网络游戏的主要特色 
  public void killBoss(); 
  
  // 升级 
  public void upgrade(); 
  
}
Salin selepas log masuk
/** 
 * 游戏者 
 * 
 */
public class GamePlayer implements IGamePlayer { 
  
  private String name = ""; 
  
  // 通过构造函数传递名称 
  public GamePlayer(String _name) { 
    this.name = _name; 
  } 
  
  // 打怪,最期望的就是杀老怪 
  
  public void killBoss() { 
  
    System.out.println(this.name + " 在打怪!"); 
  
  } 
  
  // 进游戏之前你肯定要登录吧,这是一个必要条件 
  public void login(String user, String password) { 
    System.out.println("登录名为" + user + " 的角色 " + this.name + "登录成功!"); 
  } 
  
  // 升级,升级有很多方法,花钱买是一种,做任务也是一种 
  public void upgrade() { 
    System.out.println(this.name + " 又升了一级!"); 
  } 
  
}
Salin selepas log masuk
/** 
 * 客户端 对被代理对象不可见 
 */
public class GamePlayerProxy implements IGamePlayer { 
  
  private IGamePlayer gamePlayer = null;//被代理对象 
  
  // 通过构造函数传递要对谁进行代练 
  public GamePlayerProxy(String username) { 
    this.gamePlayer = new GamePlayer(username); 
  } 
  
  // 代练杀怪 
  public void killBoss() { 
    this.gamePlayer.killBoss(); 
  } 
  
  // 代练登录 
  public void login(String user, String password) { 
    this.gamePlayer.login(user, password); 
  } 
  
  // 代练升级 
  public void upgrade() { 
    this.gamePlayer.upgrade(); 
  } 
  
}
Salin selepas log masuk
/* 
 * 客户端 对被代理对象不可见 
 */
public class GamePlayerProxy2 implements IGamePlayer { 
  
  private IGamePlayer gamePlayer = null;//被代理对象 
  
  // 通过构造函数传递要对谁进行代练 
  public GamePlayerProxy2(String username) { 
    this.gamePlayer = new GamePlayer(username); 
  } 
  
  // 代练杀怪 
  public void killBoss() { 
    this.gamePlayer.killBoss(); 
  } 
  
  // 代练登录 
  public void login(String user, String password) { 
    System.out.println("登录时间是:" + new Date().toLocaleString()); 
    this.gamePlayer.login(user, password); 
  } 
  
  // 代练升级 
  public void upgrade() { 
    this.gamePlayer.upgrade(); 
    System.out.println("升级时间是:" + new Date().toLocaleString()); 
  } 
  
}
Salin selepas log masuk
/* 
 * 客户端 对被代理对象不可见 
 */
public class GamePlayerProxy3 { 
  
  private IGamePlayer gamePlayer; 
  // 通过构造函数传递 被代练(代理)对象 
  public GamePlayerProxy3(IGamePlayer gamePlayer) { 
     this.gamePlayer = gamePlayer; 
     System.out.println("我是一名代练,我玩的角色是别人的,可以动态传递进来"); 
  } 
    
  public IGamePlayer getProxy() { 
    return (IGamePlayer) Proxy.newProxyInstance(this.getClass().getClassLoader(),  
        new Class[]{IGamePlayer.class}, new MyInvocationHandler()); 
  } 
  
  private class MyInvocationHandler implements InvocationHandler { 
    
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { 
      if (method.getName().equals("login")) { 
        System.out.println("登录时间是:" + new Date().toLocaleString()); 
      } if (method.getName().equals("upgrade")) { 
        System.out.println("升级时间是:" + new Date().toLocaleString()); 
      } 
      method.invoke(gamePlayer, args); 
      return null; 
    } 
      
  } 
}
Salin selepas log masuk
public class Test { 
  public static void main(String[] args) { 
    /* 
     * 普通的静态代理: 客户端不知道被代理对象,由代理对象完成其功能的调用 
     */ 
    IGamePlayer proxy = new GamePlayerProxy("X"); 
    System.out.println("开始时间是:" + new Date().toLocaleString()); 
    proxy.login("zhangSan", "abcd"); 
    proxy.killBoss(); 
    proxy.upgrade(); 
    System.out.println("结束时间是:" + new Date().toLocaleString()); 
      
    System.out.println(); 
      
    /* 
     * 代理对象 增强了 被代理对象的功能 
     */ 
    IGamePlayer proxy2 = new GamePlayerProxy2("M"); 
    proxy2.login("lisi", "efg"); 
    proxy2.killBoss(); 
    proxy2.upgrade(); 
      
    System.out.println(); 
      
    /* 
     * 动态代理:使用jdk提供的InvocationHandler,反射调用被代理对象的方法 
     * 结合java.reflect.Proxy 产生代理对象 
     * 动态传入被代理对象构造InvocationHandler,在handler中的invoke时可以增强被代理对象的方法的功能 
     * 或者说:(面向切面:)在什么地方(连接点), 执行什么行为(通知) 
     * GamePlayerProxy3中是方法名为login时通知开始时间,upgrade时通知结束时间 
     */ 
    GamePlayerProxy3 dynamic = new GamePlayerProxy3(new GamePlayer("Y")); 
    IGamePlayer dynamicPlayer = dynamic.getProxy(); 
    dynamicPlayer.login("wangwu", "1234"); 
    dynamicPlayer.killBoss(); 
    dynamicPlayer.upgrade(); 
    /* 
     * 面向切面: 一些相似的业务逻辑需要加在众多的地方,那们就可以把它提取到切面中, 切面也就是事务切面:如日志切面、权限切面、业务切面 
     */
  } 
}
Salin selepas log masuk

打印:

开始时间是:2014-10-8 17:19:05 
登录名为zhangSan 的角色 X登录成功! 
X 在打怪! 
X 又升了一级! 
结束时间是:2014-10-8 17:19:05 
  
登录时间是:2014-10-8 17:19:05 
登录名为lisi 的角色 M登录成功! 
M 在打怪! 
M 又升了一级! 
升级时间是:2014-10-8 17:19:05 
  
我是一名代练,我玩的角色是别人的,可以动态传递进来 
登录时间是:2014-10-8 17:19:05 
登录名为wangwu 的角色 Y登录成功! 
Y 在打怪! 
升级时间是:2014-10-8 17:19:05 
Y 又升了一级!
Salin selepas log masuk

 优点 
 (1)职责清晰 
 真实的角色就是实现实际的业务逻辑,不用关心其他非本职责的事务,通过后期的代理完成一件完成事务,附带的结果就是编程简洁清晰。 
 (2)代理对象可以在客户端和目标对象之间起到中介的作用,这样起到了的作用和保护了目标对象的作用。 
 (3)高扩展性 

更多Java使用设计模式中的代理模式构建项目的实例展示相关文章请关注PHP中文网!

Kenyataan Laman Web ini
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn

Alat AI Hot

Undresser.AI Undress

Undresser.AI Undress

Apl berkuasa AI untuk mencipta foto bogel yang realistik

AI Clothes Remover

AI Clothes Remover

Alat AI dalam talian untuk mengeluarkan pakaian daripada foto.

Undress AI Tool

Undress AI Tool

Gambar buka pakaian secara percuma

Clothoff.io

Clothoff.io

Penyingkiran pakaian AI

Video Face Swap

Video Face Swap

Tukar muka dalam mana-mana video dengan mudah menggunakan alat tukar muka AI percuma kami!

Alat panas

Notepad++7.3.1

Notepad++7.3.1

Editor kod yang mudah digunakan dan percuma

SublimeText3 versi Cina

SublimeText3 versi Cina

Versi Cina, sangat mudah digunakan

Hantar Studio 13.0.1

Hantar Studio 13.0.1

Persekitaran pembangunan bersepadu PHP yang berkuasa

Dreamweaver CS6

Dreamweaver CS6

Alat pembangunan web visual

SublimeText3 versi Mac

SublimeText3 versi Mac

Perisian penyuntingan kod peringkat Tuhan (SublimeText3)

Adakah perisian keselamatan syarikat menyebabkan aplikasi gagal dijalankan? Bagaimana cara menyelesaikan masalah dan menyelesaikannya? Adakah perisian keselamatan syarikat menyebabkan aplikasi gagal dijalankan? Bagaimana cara menyelesaikan masalah dan menyelesaikannya? Apr 19, 2025 pm 04:51 PM

Penyelesaian masalah dan penyelesaian kepada perisian keselamatan syarikat yang menyebabkan beberapa aplikasi tidak berfungsi dengan baik. Banyak syarikat akan menggunakan perisian keselamatan untuk memastikan keselamatan rangkaian dalaman. …

Bagaimana dengan elegan mendapatkan nama pemboleh ubah kelas entiti untuk membina keadaan pertanyaan pangkalan data? Bagaimana dengan elegan mendapatkan nama pemboleh ubah kelas entiti untuk membina keadaan pertanyaan pangkalan data? Apr 19, 2025 pm 11:42 PM

Apabila menggunakan Mybatis-Plus atau Rangka Kerja ORM yang lain untuk operasi pangkalan data, sering diperlukan untuk membina syarat pertanyaan berdasarkan nama atribut kelas entiti. Sekiranya anda secara manual setiap kali ...

Bagaimana untuk memudahkan isu pemetaan medan dalam dok sistem menggunakan mapstruct? Bagaimana untuk memudahkan isu pemetaan medan dalam dok sistem menggunakan mapstruct? Apr 19, 2025 pm 06:21 PM

Pemprosesan pemetaan medan dalam dok sistem sering menemui masalah yang sukar ketika melaksanakan sistem dok: bagaimana untuk memetakan medan antara muka sistem dengan berkesan ...

Bagaimanakah saya menukar nama kepada nombor untuk melaksanakan penyortiran dan mengekalkan konsistensi dalam kumpulan? Bagaimanakah saya menukar nama kepada nombor untuk melaksanakan penyortiran dan mengekalkan konsistensi dalam kumpulan? Apr 19, 2025 pm 11:30 PM

Penyelesaian untuk menukar nama kepada nombor untuk melaksanakan penyortiran dalam banyak senario aplikasi, pengguna mungkin perlu menyusun kumpulan, terutama dalam satu ...

Bagaimanakah Idea IntelliJ mengenal pasti nombor port projek boot musim bunga tanpa mengeluarkan log? Bagaimanakah Idea IntelliJ mengenal pasti nombor port projek boot musim bunga tanpa mengeluarkan log? Apr 19, 2025 pm 11:45 PM

Mula musim bunga menggunakan versi IntelliJideaultimate ...

Bagaimana dengan elegan mendapatkan syarat pertanyaan bangunan pembolehubah kelas entiti apabila menggunakan tkmybatis untuk pertanyaan pangkalan data? Bagaimana dengan elegan mendapatkan syarat pertanyaan bangunan pembolehubah kelas entiti apabila menggunakan tkmybatis untuk pertanyaan pangkalan data? Apr 19, 2025 pm 09:51 PM

Apabila menggunakan tkmybatis untuk pertanyaan pangkalan data, bagaimana dengan anggun mendapatkan nama pembolehubah kelas entiti untuk membina keadaan pertanyaan adalah masalah biasa. Artikel ini akan ...

Bagaimana cara menukar objek Java dengan selamat ke array? Bagaimana cara menukar objek Java dengan selamat ke array? Apr 19, 2025 pm 11:33 PM

Penukaran objek dan tatasusunan Java: Perbincangan mendalam tentang risiko dan kaedah penukaran jenis cast yang betul Banyak pemula Java akan menemui penukaran objek ke dalam array ...

Platform e-dagang SKU dan Reka Bentuk Pangkalan Data SPU: Bagaimana untuk mengambil kira kedua-dua atribut yang ditakrifkan oleh pengguna dan produk yang tidak berkesudahan? Platform e-dagang SKU dan Reka Bentuk Pangkalan Data SPU: Bagaimana untuk mengambil kira kedua-dua atribut yang ditakrifkan oleh pengguna dan produk yang tidak berkesudahan? Apr 19, 2025 pm 11:27 PM

Penjelasan terperinci mengenai reka bentuk jadual SKU dan SPU di platform e-dagang Artikel ini akan membincangkan isu reka bentuk pangkalan data SKU dan SPU dalam platform e-dagang, terutamanya bagaimana menangani jualan yang ditentukan pengguna ...

See all articles