【设计模式】代理模式例子解析

代理模式,顾名思义,就是我们在需要访问一个类时,并不直接调用这个类,而是通过一个"代理"来间接地实现这个过程。

这个"代理"就像是真实对象的一个接口,所有的对于真实对象的操作都需要通过这个"代理"来实现。"郑重其事的代理",这或许是代理模式的最好解释。在计算机科学领域,代理模式是一种设计模式,它通过为其他对象提供一个类型为代理或占位符的替身,以控制对这个对象的访问。使用代理模式,可以在不改变接口的前提下实现对目标对象的控制访问。

举个最日常的例子,现实生活中代理的例子,比如我们去外国旅行,可能不会直接预定酒店和买机票,而是找一个旅行社作为我们的代理。这个旅行社就会代表我们去做这些事情。同样地,编程中的代理模式也遵循这个原理。

代理模式的应用

  1. 远程代理:这是一种常见的应用场景,当我们需要访问一个远程服务时,通常不能直接访问,而是需要通过网络、协议等进行转换,此时就可以使用远程代理。例如,我们可能会在本地创建一个代理对象,这个对象内部封装了所有的网络通信等细节,我们使用这个对象就像使用本地对象一样。
  2. 虚拟代理:该模式常用于控制访问一些资源消耗大的对象。比如你有一个大图像需要加载,当用户操作这个图像时,我们可能不会立即加载,而是先显示一个占位符(代理),只有当真正需要的时候才会进行加载。
  3. 安全代理:这种类型的代理用于控制真实对象的访问权限,只有通过安全检查的请求才能访问真实对象。比如,有些对象有对其访问和操作的权限限制,我们可以把权限的处理逻辑放到代理中。
  4. 智能指引:这是一种复杂的代理模式,它不仅仅控制对真实对象的访问,还可以全方位地控制和协调。例如C++的智能指针,它可以记录一个对象被引用的次数,当对象的引用次数降为0时,智能指针就会自动销毁这个对象。

代码实现

我将针对代理模式的四个关键应用场景:远程代理、虚拟代理、安全代理和智能指引,深入地探讨它们在实际中的应用,并使用代码(Go和Java)进行说明。

1. 远程代理

远程代理主要处理不在本地计算机的对象。代理对象扮演着远程对象的本地代表,所有对远程对象的操作都通过代理对象完成。

Go示例:

go 复制代码
//使用Go的rpc库进行远程代理示例,这里仅作示例,并〔非真实运行代码。
type RemoteServer struct{}

func (r *RemoteServer) SayHello(arg *int, reply *string) error {
    *reply = "Hello from remote server"
    return nil
}

type Proxy struct {
    client *rpc.Client
}

func (p *Proxy) SayHello() string {
    var reply string
    err := p.client.Call("RemoteServer.SayHello", new(int), &reply)
    if err != nil {
        log.Fatal("Error :", err)
    }
    return reply
}

func main() {
    client, _ := rpc.DialHTTP("tcp", "127.0.0.1:1234")
    proxy := &Proxy{client: client}
    fmt.Println(proxy.SayHello()) //print: Hello from remote server
}

2. 虚拟代理

虚拟代理用于处理大规模资源的对象,比如大图像或者网络资源。在真正需要时,再去创建或加载这个资源。

3. 安全代理

安全代理用于控制真实对象的访问权限,只有通过安全检查的请求才能访问真实对象。比如,有些对象有对其访问和操作的权限限制,我们可以把权限的处理逻辑放到代理中。

Go示例:

go 复制代码
//文件模块接口
type File interface {
    Read(name string) string
}

//真实的文件模块
type RealFile struct{}

func (RealFile) Read(name string) string {
    return "读取文件" + name
}

// ProxyFile作为一个代理,提供额外的安全检查
type ProxyFile struct {
    file RealFile
}

func (p ProxyFile) Read(name string) string {
    // 额外的安全检查
    if len(name) > 10 {
        return "文件名过长,不允许访问。"
    }
    return p.file.Read(name)
}

4. 智能指引

智能指引是为一个对象提供一种代理,并在一些特定的情况下选择提供一种"智能"的操作方式。比如引用计数,如果一个对象进行指向操作,其引用计数+1;如果进行解引用操作,其引用计数-1,等到引用计数为0时,可以自动回收对象。

代理模式的优缺点

  • 优点:首先,代理模式能够协调调用者和被调用者,在一定程度上降低了系统的耦合度。其次,代理对象作为客户端和目标对象之间的中介,起到了保护目标对象的作用。
  • 缺点:代理模式会导致请求处理速度变慢,同时增加了系统的复杂性。

如果上面的内容对你有帮助,请点赞收藏哦,我会分享更多的经验~

相关推荐
腾讯TNTWeb前端团队6 小时前
helux v5 发布了,像pinia一样优雅地管理你的react状态吧
前端·javascript·react.js
千千寰宇9 小时前
[设计模式/Java/多线程] 设计模式之单例模式【9】
设计模式·操作系统-进程/线程/并发
uhakadotcom9 小时前
视频直播与视频点播:基础知识与应用场景
后端·面试·架构
范文杰9 小时前
AI 时代如何更高效开发前端组件?21st.dev 给了一种答案
前端·ai编程
拉不动的猪9 小时前
刷刷题50(常见的js数据通信与渲染问题)
前端·javascript·面试
拉不动的猪9 小时前
JS多线程Webworks中的几种实战场景演示
前端·javascript·面试
FreeCultureBoy10 小时前
macOS 命令行 原生挂载 webdav 方法
前端
uhakadotcom11 小时前
快速开始使用 n8n
后端·面试·github
uhakadotcom11 小时前
Astro 框架:快速构建内容驱动型网站的利器
前端·javascript·面试
uhakadotcom11 小时前
了解Nest.js和Next.js:如何选择合适的框架
前端·javascript·面试