.netCore用DispatchProxy实现动态代理
在 .NET Core 中,你可以使用 DispatchProxy 类来实现动态代理。DispatchProxy 允许你在运行时创建一个代理对象,该代理对象可以拦截对其所代理的对象的方法调用,并在方法调用前后执行自定义的逻辑。这在 AOP(面向切面编程)和其他一些场景中非常有用。
以下是一个简单的示例,演示如何使用 DispatchProxy 实现动态代理:
首先,你需要创建一个实现了 DispatchProxy 抽象类的代理类,并重写其中的 Invoke 方法。在 Invoke 方法中,你可以添加自己的逻辑,比如在方法调用前后执行一些操作。
using System;
using System.Reflection;
using System.Threading.Tasks;
using System.Runtime.CompilerServices;
using System.Runtime.Remoting.Messaging;public class MyProxy<T> : DispatchProxy
{private T _decorated;protected override object Invoke(MethodInfo targetMethod, object[] args){Console.WriteLine($"Before invoking method {targetMethod.Name}");// 在调用目标方法之前、之后,可以添加自己的逻辑var result = targetMethod.Invoke(_decorated, args);Console.WriteLine($"After invoking method {targetMethod.Name}");return result;}public static T Create(T decorated){object proxy = Create<T, MyProxy<T>>();((MyProxy<T>)proxy)._decorated = decorated;return (T)proxy;}
}
接下来,你可以创建一个接口或类,然后实例化代理对象并使用它:
public interface ICalculator
{int Add(int a, int b);int Subtract(int a, int b);
}public class Calculator : ICalculator
{public int Add(int a, int b){return a + b;}public int Subtract(int a, int b){return a - b;}
}class Program
{static void Main(string[] args){ICalculator calculator = new Calculator();// 创建代理对象ICalculator proxy = MyProxy<ICalculator>.Create(calculator);int result = proxy.Add(5, 3);Console.WriteLine($"Result: {result}");result = proxy.Subtract(10, 4);Console.WriteLine($"Result: {result}");}
}
在上面的示例中,MyProxy 类是一个泛型类,它接受一个类型参数 T,代表你要代理的接口或类。在 Invoke 方法中,你可以添加你需要的逻辑,例如在方法调用前后打印日志。然后,通过调用 MyProxy.Create 方法,你可以创建一个代理对象,该对象实现了你指定的接口或类,并且会拦截方法调用并执行你的逻辑。
需要注意的是,DispatchProxy 只支持接口的代理。如果你要代理的是一个类而不是接口,你可能需要考虑其他的代理库,如 Castle DynamicProxy 或 LinFu。
当你使用动态代理时,你可以创建一个中间对象(代理对象),该对象可以拦截对另一个对象(目标对象)的方法调用,并在方法调用前后执行自定义的逻辑。这种技术通常用于实现横切关注点,例如日志记录、性能监测、事务管理等,而无需修改目标对象的代码。
在 .NET Core 中,DispatchProxy
是一个抽象类,允许你创建动态代理对象。它的作用是生成一个代理类,该代理类实现了一个接口,并在接口的方法调用时执行自定义的操作。以下是我上面提供的动态代理示例的详细解释:
-
创建代理类
MyProxy<T>
:- 这个类是一个泛型类,它接受一个类型参数
T
,代表你要代理的接口或类。 - 该类继承自
DispatchProxy
,这意味着它是一个动态代理类。 - 在
MyProxy<T>
类中,你重写了Invoke
方法。Invoke
方法是DispatchProxy
提供的一个虚拟方法,当代理对象调用其实现的接口方法时,Invoke
方法会被调用。 - 在
Invoke
方法中,你可以添加自己的逻辑。在示例中,我简单地在方法调用前后打印了一条日志。
- 这个类是一个泛型类,它接受一个类型参数
-
创建目标接口和类:
- 在示例中,我创建了一个简单的接口
ICalculator
,以及一个实现了该接口的类Calculator
。这个类有两个方法:Add
和Subtract
。
- 在示例中,我创建了一个简单的接口
-
创建代理对象:
- 在
Main
方法中,首先实例化了一个Calculator
类的对象,并将其赋给calculator
变量。 - 然后,通过调用
MyProxy<ICalculator>.Create(calculator)
创建了一个代理对象,该代理对象实现了ICalculator
接口,并包装了calculator
对象。
- 在
-
使用代理对象:
- 接下来,你可以使用代理对象
proxy
来调用接口方法,例如proxy.Add(5, 3)
和proxy.Subtract(10, 4)
。 - 由于代理对象是通过
MyProxy<ICalculator>.Create
创建的,它会拦截这些方法调用,并在方法调用前后执行Invoke
方法中定义的逻辑,这里是打印日志。
- 接下来,你可以使用代理对象
总之,DispatchProxy
的作用是允许你在运行时创建一个代理对象,该对象可以拦截方法调用并执行自定义的逻辑。这可以用于实现各种横切关注点,而不需要修改目标对象的代码,从而使代码更加可维护和可扩展。在示例中,我们使用 DispatchProxy
创建了一个简单的日志记录代理,但你可以根据需要添加其他功能。
相关文章:
.netCore用DispatchProxy实现动态代理
在 .NET Core 中,你可以使用 DispatchProxy 类来实现动态代理。DispatchProxy 允许你在运行时创建一个代理对象,该代理对象可以拦截对其所代理的对象的方法调用,并在方法调用前后执行自定义的逻辑。这在 AOP(面向切面编程…...

好奇喵 | Tor浏览器——访问.onion网址,揭开Dark Web的神秘面纱
前言 在之前的博客中: 1.Surface Web —> Deep Web —> Dark Web,我们解释了表层网络、深层网络等的相关概念; 2.Tor浏览器——层层剥开洋葱,我们阐述了Tor的历史和基本工作原理; 3.Tor浏览器…...

Maven 中引用其他项目jar包出现BOOT-INF问题
问题 在B项目中引入A项目的类,但是发现怎么也引入不进来 A项目打包之后,想在B项目中引用jar 在B项目中发现类文件无法引用 参考网上进行清缓存等一系列操作都没有解决。 最后发现引用的jar包中包含BOOT-INF, 然后去A项目中查找ÿ…...
PHP框架面试题
目录 1、什么是PHP框架? 2、常见的PHP框架有哪些? 3、为什么要使用PHP框架? 4、什么是路由?PHP框架中的路由是如何实现的? 5.TP的特性有哪些? 6.laravel有那些特点? 7.TP框架和Laravel框架的区别 8.tp5和tp6区…...

如何清理C盘
当前最棘手的问题是C盘满了,如何清理成了一个大问题,在本篇文章中我将记录我在清理c盘空间过程中的探索。 2023-10-06探索无果,记录于此。...
计算机网络基础知识
1 计算机网络是指将多台计算机连接在一起,以便它们可以相互通信和共享资源的系统。在本文中,我们将详细介绍计算机网络的基础知识,包括网络的分类、网络协议、网络拓扑、网络设备和网络安全等方面的内容。 网络分类 计算机网络可以根据其范…...

Go语言面经进阶10问
1.Golang可变参数 函数方法的参数,可以是任意多个,这种我们称之为可以变参数,比如我们常用的fmt.Println()这类函数,可以接收一个可变的参数。可以变参数,可以是任意多个。我们自己也可以定义可以变参数,可…...
大厂真题:【DP】米哈游2023秋招-米小游与魔法少女-奇运
题目描述与示例 题目描述 米小游都快保底了还没抽到希儿,好生气哦!只能打会活动再拿点水晶。 米小游和世界第一可爱的魔法少女 TeRiRi 正在打 BOSS,BOSS 的血量为h,当 BOSS 血量小于等于0时,BOSS 死亡。TeRiRi 有一…...

后端面经学习自测(一)
文章目录 1、MySQL-MVCC2、MySQL-原子性怎么实现3、MySQL-持久性怎么实现隔离性怎么实现 4、操作系统-死锁产生手写死锁死锁排查 5、操作系统-避免死锁死锁的四个必要条件预防死锁 6、操作系统-pageCache是什么零拷贝 7、计算机网络-TCP的可靠性和顺序性怎么实现8、计算机网络-…...
win10、win11安装Ubuntu 22.04
目前为止(2023年10月6日),最新的 Ubuntu 版本是 Ubuntu 22.04。你可以按照以下步骤在 Windows 上使用 WSL 安装 Ubuntu 22.04: 检查系统要求: 确保你的操作系统是 Windows 10 或更高版本,并已安装 Windows …...

golang gin框架1——简单案例以及api版本控制
gin框架 gin是golang的一个后台WEB框架 简单案例 package mainimport ("github.com/gin-gonic/gin""net/http" )func main() {r : gin.Default()r.GET("/ping", func(c *gin.Context) {//以json形式输出,还可以xml protobufc.JSON…...
Redisson—分布式对象
每个Redisson对象实例都会有一个与之对应的Redis数据实例,可以通过调用getName方法来取得Redis数据实例的名称(key)。 RMap map redisson.getMap("mymap"); map.getName(); // mymap 所有与Redis key相关的操作都归纳在RKeys这…...
alsa pcm接口之在unix环境的传输方法
在unix环境,数据片段响应被接受通过standard I/O call或事件等待路径(poll或select功能),为完成列表,异步通知响应该被列举出来.ALSA实现那些方法被描述在ALSA transfers部分. 标准I/O传输(Standadrd I/O transfers) 这个标准I/O传输常常使用read和write C语言函数集,对于那些函…...

小谈设计模式(20)—组合模式
小谈设计模式(20)—组合模式 专栏介绍专栏地址专栏介绍 组合模式对象类型叶节点组合节点 核心思想应用场景123 结构图结构图分析 Java语言实现首先,我们需要定义一个抽象的组件类 Component,它包含了组合节点和叶节点的公共操作&a…...

sheng的学习笔记-【中文】【吴恩达课后测验】Course 1 - 神经网络和深度学习 - 第三周测验
课程1_第3周_测验题 目录:目录 第一题 1.以下哪一项是正确的? A. 【 】 a [ 2 ] ( 12 ) a^{[2](12)} a[2](12)是第12层,第2个训练数据的激活向量。 B. 【 】X是一个矩阵,其中每个列都是一个训练示例。 C. 【 】 a 4 […...

一文详解动态链表和静态链表的区别
1、引言 本文主要是对动态链表和静态链表的区别进行原理上的讲解分析,先通过对顺序表和动态链表概念和特点的原理性介绍,进而引申出静态链表的作用,以及其概念。通过这些原理性的概述,最后总结归纳出动态链表和静态链表的区别。本…...

[C国演义] 第十三章
第十三章 三数之和四数之和 三数之和 力扣链接 根据题目要求: 返回的数对应的下标各不相同三个数之和等于0不可包含重复的三元组 – – 即顺序是不做要求的 如: [-1 0 1] 和 [0, 1, -1] 是同一个三元组输出答案顺序不做要求 暴力解法: 排序 3个for循环 去重 — — N^3, …...

<二>Qt斗地主游戏开发:过场动画的实现
1. 过场动画效果 2. 思路分析 过场动画较为简单,只有一个进度条在进行滚动,因此实现起来不需要动画相关处理,仅需要图片和定时器设定,让进度条动起来即可。我们可以创建一个对话框,设定背景图片以及对话框透明无边框&a…...
链式法则(Chain Rule)
定义 链式法则(Chain Rule)是概率论和统计学中的一个基本原理,用于计算联合概率分布或条件概率分布的乘积。它可以用于分解一个复杂的概率分布为多个较简单的条件概率分布的乘积,从而简化概率分析问题。 链式法则有两种常见的形…...

AUTOSAR COM模块框架梳理
框架: COM的功能主要就是两个: 把IPDU内的signal提取出来提供给SWC使用,把SWC发送的signal拷贝到IPDU buffer内 所以,COM的关键字是 signal, signal group, IPDU, IPDU group Signal group 是为了保证 Complex Data Types 的数…...

微信小程序之bind和catch
这两个呢,都是绑定事件用的,具体使用有些小区别。 官方文档: 事件冒泡处理不同 bind:绑定的事件会向上冒泡,即触发当前组件的事件后,还会继续触发父组件的相同事件。例如,有一个子视图绑定了b…...
day52 ResNet18 CBAM
在深度学习的旅程中,我们不断探索如何提升模型的性能。今天,我将分享我在 ResNet18 模型中插入 CBAM(Convolutional Block Attention Module)模块,并采用分阶段微调策略的实践过程。通过这个过程,我不仅提升…...

【HarmonyOS 5.0】DevEco Testing:鸿蒙应用质量保障的终极武器
——全方位测试解决方案与代码实战 一、工具定位与核心能力 DevEco Testing是HarmonyOS官方推出的一体化测试平台,覆盖应用全生命周期测试需求,主要提供五大核心能力: 测试类型检测目标关键指标功能体验基…...

visual studio 2022更改主题为深色
visual studio 2022更改主题为深色 点击visual studio 上方的 工具-> 选项 在选项窗口中,选择 环境 -> 常规 ,将其中的颜色主题改成深色 点击确定,更改完成...
基于服务器使用 apt 安装、配置 Nginx
🧾 一、查看可安装的 Nginx 版本 首先,你可以运行以下命令查看可用版本: apt-cache madison nginx-core输出示例: nginx-core | 1.18.0-6ubuntu14.6 | http://archive.ubuntu.com/ubuntu focal-updates/main amd64 Packages ng…...

涂鸦T5AI手搓语音、emoji、otto机器人从入门到实战
“🤖手搓TuyaAI语音指令 😍秒变表情包大师,让萌系Otto机器人🔥玩出智能新花样!开整!” 🤖 Otto机器人 → 直接点明主体 手搓TuyaAI语音 → 强调 自主编程/自定义 语音控制(TuyaAI…...
css3笔记 (1) 自用
outline: none 用于移除元素获得焦点时默认的轮廓线 broder:0 用于移除边框 font-size:0 用于设置字体不显示 list-style: none 消除<li> 标签默认样式 margin: xx auto 版心居中 width:100% 通栏 vertical-align 作用于行内元素 / 表格单元格ÿ…...

网络编程(UDP编程)
思维导图 UDP基础编程(单播) 1.流程图 服务器:短信的接收方 创建套接字 (socket)-----------------------------------------》有手机指定网络信息-----------------------------------------------》有号码绑定套接字 (bind)--------------…...
代码随想录刷题day30
1、零钱兑换II 给你一个整数数组 coins 表示不同面额的硬币,另给一个整数 amount 表示总金额。 请你计算并返回可以凑成总金额的硬币组合数。如果任何硬币组合都无法凑出总金额,返回 0 。 假设每一种面额的硬币有无限个。 题目数据保证结果符合 32 位带…...

免费PDF转图片工具
免费PDF转图片工具 一款简单易用的PDF转图片工具,可以将PDF文件快速转换为高质量PNG图片。无需安装复杂的软件,也不需要在线上传文件,保护您的隐私。 工具截图 主要特点 🚀 快速转换:本地转换,无需等待上…...