cglib动态代理、jdk动态代理及spring动态代理使用

news2024/11/17 15:59:25

1.项目初始化

1.1 pom.xml

<dependencies>
        <!-- spring依赖 -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>5.2.5.RELEASE</version>
        </dependency>
        <!-- spring事务依赖 -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-tx</artifactId>
            <version>5.2.5.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-jdbc</artifactId>
            <version>5.2.5.RELEASE</version>
        </dependency>
        <!-- mybatis依赖 -->
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.5.1</version>
        </dependency>
        <!-- mybatis和spring集成依赖 -->
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis-spring</artifactId>
            <version>1.3.1</version>
        </dependency>
        <!-- mysql驱动 -->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.9</version>
        </dependency>
        <!-- 阿里的连接池 -->
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>druid</artifactId>
            <version>1.1.12</version>
        </dependency>
        <!-- aspectj-->
        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjrt</artifactId>
            <version>1.9.5</version>
        </dependency>
         <dependency>
            <groupId>org.apache.geronimo.bundles</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>1.6.8_2</version>
        </dependency>
    </dependencies>

1.2UserService对象

package com.nq.service;

import org.springframework.stereotype.Component;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:04
 */
@Component
public class UserService {

    public void test(){
        System.out.println("test方法。");
    }

    public void a(){
        System.out.println("a方法。");
    }
}

在这里插入图片描述

2.cjlib动态代理的使用

2.1所有的方法都是使用动态代理

package com.nq.service;

import org.springframework.cglib.proxy.Callback;
import org.springframework.cglib.proxy.Enhancer;
import org.springframework.cglib.proxy.MethodInterceptor;
import org.springframework.cglib.proxy.MethodProxy;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:29
 */
public class CglibTest {
    public static void main(String[] args) {
        UserService target =new UserService();

        Enhancer enhancer=new Enhancer();
        enhancer.setSuperclass(UserService.class);

        enhancer.setCallbacks(new Callback[]{new MethodInterceptor() {
                    @Override
                    public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
                        System.out.println("before...");

                        //被代理的对象,目标方法
                        //Object result=methodProxy.invoke(target,objects);
                        //Object result=method.invoke(target,objects);
                        Object result=methodProxy.invokeSuper(o,objects);


                        System.out.println("After...");
                        return  result;
                    }
                }
        });

        UserService userService = (UserService) enhancer.create();
        userService.test();
    }
}

2.2不同的方法使用不同的代理

package com.nq.service;

import org.springframework.cglib.proxy.*;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:29
 */
public class CglibTest {
    public static void main(String[] args) {
        UserService target =new UserService();

        Enhancer enhancer=new Enhancer();
        enhancer.setSuperclass(UserService.class);

        enhancer.setCallbacks(new Callback[]{new MethodInterceptor() {
                    @Override
                    public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
                        System.out.println("before...");

                        //被代理的对象,目标方法
                        //Object result=methodProxy.invoke(target,objects);
                        //Object result=method.invoke(target,objects);
                        Object result=methodProxy.invokeSuper(o,objects);


                        System.out.println("After...");
                        return  result;
                    }
                }
                , NoOp.INSTANCE});

        enhancer.setCallbackFilter(new CallbackFilter() {
            @Override
            public int accept(Method method) {
                if("test".equals(method.getName())){//表示test方法执行第一个代理方法,其他方法执行第二个方法
                    return 0;
                }else{
                    return 1;
                }
            }
        });
        UserService userService = (UserService) enhancer.create();
        userService.a();
    }
}

3.jdk动态代理的使用

3.1UserInterface创建接口

package com.nq.service;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:58
 */
public interface UserInterface {

    void test();

    void a();
}

3.2UserService实现接口

package com.nq.service;

import org.springframework.stereotype.Component;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:04
 */
@Component
public class UserService implements UserInterface{

    public void test(){
        System.out.println("test方法。");
    }

    public void a(){
        System.out.println("a方法。");
    }
}

3.3JdkTest代理的main方法

package com.nq.service;


import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:56
 */
public class JdkTest {
    public static void main(String[] args) {
        UserInterface target=new UserService();
        UserInterface userInterface =(UserInterface) Proxy.newProxyInstance(JdkTest.class.getClassLoader(), new Class[]{UserInterface.class}, new InvocationHandler() {
            @Override
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                System.out.println("Jdk动态代理被执行了,方法之前");
                method.invoke(target,args);
                System.out.println("Jdk动态代理被执行了,方法之后");
                return null;
            }
        });
        userInterface.test();
    }
}

在这里插入图片描述

4.spring中动态代理的使用

4.1proxyFactory 动态代理的使用方法

NickelBeforeAdvice.java方法执行之前

package com.nq.advice;

import org.springframework.aop.BeforeAdvice;
import org.springframework.aop.MethodBeforeAdvice;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 0:59
 */
public class NickelBeforeAdvice implements MethodBeforeAdvice {
    @Override
    public void before(Method method, Object[] objects, Object o) throws Throwable {
        System.out.println("方法执行前被执行了");
    }
}

NickelAfterReturningAdvice.java方法执行之后

package com.nq.advice;

import org.aspectj.lang.annotation.AfterReturning;
import org.springframework.aop.AfterReturningAdvice;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 0:59
 */
public class NickelAfterReturningAdvice implements AfterReturningAdvice {
    @Override
    public void afterReturning(Object o, Method method, Object[] objects, Object o1) throws Throwable {
        System.out.println("方法returning被执行了");
    }
}

NickelAroundadvice.java环绕方法

package com.nq.advice;

import org.aopalliance.intercept.MethodInterceptor;
import org.aopalliance.intercept.MethodInvocation;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 0:59
 */
public class NickelAroundadvice implements MethodInterceptor {
    @Override
    public Object invoke(MethodInvocation invocation) throws Throwable {
        System.out.println("方法执行round之前");
        Object proceed = invocation.proceed();
        System.out.println("方法执行round之后");
        return proceed;
    }
}

NickelThrowAdvice.java抛异常方法

package com.nq.advice;

import org.springframework.aop.ThrowsAdvice;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 1:00
 */
public class NickelThrowAdvice implements ThrowsAdvice {

    public void afterThrowing(Method method, Object[] args, Object target, NullPointerException ex) {
        System.out.println("方法抛异常执行了");
    }
}

UserService.java抛异常方法

package com.nq.service;

import org.springframework.stereotype.Component;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:04
 */
@Component
public class UserService implements UserInterface{

    public void test(){
        System.out.println("test方法。");
    }

    public void a(){
        System.out.println("a方法。");
        throw  new NullPointerException();
    }
}

SpringProxtFactoryTest.java测试方法

package com.nq.service;

import com.nq.advice.NickelAfterReturningAdvice;
import com.nq.advice.NickelAroundadvice;
import com.nq.advice.NickelBeforeAdvice;
import com.nq.advice.NickelThrowAdvice;
import org.springframework.aop.MethodBeforeAdvice;
import org.springframework.aop.framework.ProxyFactory;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 0:49
 */
public class SpringProxtFactoryTest {
    public static void main(String[] args) {
        UserService target=new UserService();

        ProxyFactory proxyFactory=new ProxyFactory();
        proxyFactory.setTarget(target);
        //proxyFactory.setInterfaces(UserInterface.class);这里可以指定为接口类型
        proxyFactory.addAdvice(new NickelAroundadvice());
        proxyFactory.addAdvice(new NickelBeforeAdvice());
        UserService userService = (UserService) proxyFactory.getProxy();
        userService.test();

    }
}

在这里插入图片描述

4.2proxyFactory 对方法名字进行限制

NickelStaticMethodMatherPointcut.java方法匹配的方法

package com.nq.advice;

import org.springframework.aop.support.StaticMethodMatcherPointcut;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 1:39
 */
public class NickelStaticMethodMatherPointcut extends StaticMethodMatcherPointcut {
    @Override
    public boolean matches(Method method, Class<?> aClass) {
        return method.getName().equals("test");
    }
}

NickelPointcutAdvisor.java切面方法

package com.nq.advice;

import org.aopalliance.aop.Advice;
import org.springframework.aop.Pointcut;
import org.springframework.aop.PointcutAdvisor;
import org.springframework.aop.support.StaticMethodMatcherPointcut;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 1:34
 */
public class NickelPointcutAdvisor implements PointcutAdvisor {
    @Override
    public Pointcut getPointcut() {
        return new NickelStaticMethodMatherPointcut();
    }

    @Override
    public Advice getAdvice() {
        return new NickelBeforeAdvice();
    }

    @Override
    public boolean isPerInstance() {
        return false;
    }
}

SpringProxtFactoryTest.java测试的方法

package com.nq.service;

import com.nq.advice.*;
import org.springframework.aop.MethodBeforeAdvice;
import org.springframework.aop.framework.ProxyFactory;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 0:49
 */
public class SpringProxtFactoryTest {
    public static void main(String[] args) {
        UserService target=new UserService();

        ProxyFactory proxyFactory=new ProxyFactory();
        proxyFactory.setTarget(target);
        //proxyFactory.setInterfaces(UserInterface.class);这里可以指定为接口类型
        //proxyFactory.addAdvice(new NickelAroundadvice());
        //proxyFactory.addAdvice(new NickelBeforeAdvice());
        proxyFactory.addAdvisor(new NickelPointcutAdvisor());
        UserService userService = (UserService) proxyFactory.getProxy();
        userService.test();

    }
}

在这里插入图片描述
在这里插入图片描述

4.3spring中的动态代理方式

4.3.1spring执行方法时候启动逻辑

UserService.java修改

package com.nq.service;

import org.springframework.stereotype.Component;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:04
 */
public class UserService{

    public void test(){
        System.out.println("test方法。");
    }

    public void a(){
        System.out.println("a方法。");
        //throw  new NullPointerException();
    }
}

说明:这里需要去掉Component注解


AppConfig.java配置

package com.nq.service;


import com.nq.advice.NickelAfterReturningAdvice;
import com.nq.advice.NickelBeforeAdvice;
import org.springframework.aop.framework.ProxyFactoryBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/28 14:59
 */
@ComponentScan("com.nq")
public class AppConfig {

    @Bean
    public ProxyFactoryBean userService(){
        UserService userService=new UserService();
        ProxyFactoryBean proxyFactoryBean=new ProxyFactoryBean();
        proxyFactoryBean.addAdvice(new NickelAfterReturningAdvice());
        proxyFactoryBean.setTarget(userService);
        return proxyFactoryBean;
    }

}

Test.java配置

package com.nq.service;

import org.springframework.context.annotation.AnnotationConfigApplicationContext;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:00
 */

public class Test {
    public static void main(String[] args) {
        AnnotationConfigApplicationContext context=new AnnotationConfigApplicationContext();
        context.register(AppConfig.class);
        context.refresh();

        UserService userService = (UserService) context.getBean("userService");
        userService.test();
    }
}

启动Test.java显示结果
在这里插入图片描述

4.3.2不去掉注解,spring执行方法的时候执行对应的逻辑

修改NickelAfterReturningAdvice.Java,增加注解

package com.nq.advice;

import org.aspectj.lang.annotation.AfterReturning;
import org.springframework.aop.AfterReturningAdvice;
import org.springframework.stereotype.Component;

import java.lang.reflect.Method;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 0:59
 */
@Component
public class NickelAfterReturningAdvice implements AfterReturningAdvice {
    @Override
    public void afterReturning(Object o, Method method, Object[] objects, Object o1) throws Throwable {
        System.out.println("方法returning被执行了");
    }
}

修改UserService.Java,增加注解

package com.nq.service;

import org.springframework.stereotype.Component;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:04
 */
@Component
public class UserService{

    public void test(){
        System.out.println("test方法。");
    }

    public void a(){
        System.out.println("a方法。");
        //throw  new NullPointerException();
    }
}

修改AppConfig.Java配置文件

package com.nq.service;


import com.nq.advice.NickelAfterReturningAdvice;
import com.nq.advice.NickelBeforeAdvice;
import org.springframework.aop.framework.ProxyFactoryBean;
import org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/28 14:59
 */
@ComponentScan("com.nq")
public class AppConfig {

    @Bean
    public BeanNameAutoProxyCreator beanNameAutoProxyCreator(){
        BeanNameAutoProxyCreator beanNameAutoProxyCreator=new BeanNameAutoProxyCreator();
        beanNameAutoProxyCreator.setBeanNames("userSe*");
        beanNameAutoProxyCreator.setInterceptorNames("nickelAfterReturningAdvice");
        beanNameAutoProxyCreator.setProxyTargetClass(true);
        return  beanNameAutoProxyCreator;
    }

}

Test.Java配置文件

package com.nq.service;

import org.springframework.context.annotation.AnnotationConfigApplicationContext;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/29 23:00
 */

public class Test {
    public static void main(String[] args) {
        AnnotationConfigApplicationContext context=new AnnotationConfigApplicationContext();
        context.register(AppConfig.class);
        context.refresh();

        UserService userService = (UserService) context.getBean("userService");
        userService.test();
    }
}

Test测试结果
在这里插入图片描述

4.3.3AppConfig另外实现动态代理

package com.nq.service;


import com.nq.advice.NickelAfterReturningAdvice;
import com.nq.advice.NickelBeforeAdvice;
import org.springframework.aop.framework.DefaultAdvisorChainFactory;
import org.springframework.aop.framework.ProxyFactoryBean;
import org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.aop.support.DefaultPointcutAdvisor;
import org.springframework.aop.support.NameMatchMethodPointcut;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/28 14:59
 */
@ComponentScan("com.nq")
public class AppConfig {

    @Bean
    public DefaultPointcutAdvisor defaultPointcutAdvisor(){
        NameMatchMethodPointcut pointcut=new NameMatchMethodPointcut();
        pointcut.addMethodName("test");

        DefaultPointcutAdvisor defaultPointcutAdvisor=new DefaultPointcutAdvisor();
        defaultPointcutAdvisor.setPointcut(pointcut);
        defaultPointcutAdvisor.setAdvice(new NickelAfterReturningAdvice());
        return defaultPointcutAdvisor;
    }

    @Bean
    public DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator(){
        DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator=new DefaultAdvisorAutoProxyCreator();
        return defaultAdvisorAutoProxyCreator;
    }

}

测试结果
在这里插入图片描述
其中DefaultAdvisorAutoProxyCreator通过导入的方式

package com.nq.service;


import com.nq.advice.NickelAfterReturningAdvice;
import com.nq.advice.NickelBeforeAdvice;
import org.springframework.aop.framework.DefaultAdvisorChainFactory;
import org.springframework.aop.framework.ProxyFactoryBean;
import org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.aop.support.DefaultPointcutAdvisor;
import org.springframework.aop.support.NameMatchMethodPointcut;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Import;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/28 14:59
 */
@ComponentScan("com.nq")
@Import(DefaultAdvisorAutoProxyCreator.class)
public class AppConfig {

    @Bean
    public DefaultPointcutAdvisor defaultPointcutAdvisor(){
        NameMatchMethodPointcut pointcut=new NameMatchMethodPointcut();
        pointcut.addMethodName("test");

        DefaultPointcutAdvisor defaultPointcutAdvisor=new DefaultPointcutAdvisor();
        defaultPointcutAdvisor.setPointcut(pointcut);
        defaultPointcutAdvisor.setAdvice(new NickelAfterReturningAdvice());
        return defaultPointcutAdvisor;
    }
}

在这里插入图片描述

4.4spring中Aspect的使用

创建NickelAspect.java

package com.nq.aspect;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.springframework.stereotype.Component;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/30 2:37
 */
@Aspect
@Component
public class NickelAspect {

    @Before("execution(public void com.nq.service.UserService.test())")
    public void nickelBefore(JoinPoint joinPoint){
        System.out.println("NickelAspect执行了");
    }
}

修改AppConfig.java扫描类

package com.nq.service;


import com.nq.advice.NickelAfterReturningAdvice;
import com.nq.advice.NickelBeforeAdvice;
import org.springframework.aop.aspectj.annotation.AnnotationAwareAspectJAutoProxyCreator;
import org.springframework.aop.framework.DefaultAdvisorChainFactory;
import org.springframework.aop.framework.ProxyFactoryBean;
import org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.aop.support.DefaultPointcutAdvisor;
import org.springframework.aop.support.NameMatchMethodPointcut;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.EnableAspectJAutoProxy;
import org.springframework.context.annotation.Import;

/**
 * @author Nickel
 * @version 1.0
 * @date 2023/7/28 14:59
 */
@ComponentScan("com.nq")
@Import(AnnotationAwareAspectJAutoProxyCreator.class)
//@EnableAspectJAutoProxy
public class AppConfig {

}

启动测试类测试
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/809849.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

6个电池均衡,buckboost电路,精度高,均衡速度快,BMS均衡

6个电池均衡&#xff0c;buckboost电路&#xff0c;精度高&#xff0c;均衡速度快&#xff0c;本人原创。 1、主体电路图如下 2、均衡电压如图 3、平均电压波动图

SpringBoot使用PropertiesLauncher加载外部jar包

启用SpringBoot的PropertiesLauncher 使用SpringBoot的PropertiesLauncher可以优先加载外部的jar文件, 这样可以在程序运行前替换jar包, 官方文档: Launching Executable Jars 使用演示 建立一个SpringBoot工程, 工程中依赖一个叫自定义的utils包, 版本是1.0.0, 通过http接口…

Java基础_网络编程

Java基础_网络编程 网络编程三要素InetAddress网络模型 UDP通信程序单播发送数据接收数据聊天室 组播广播 TCPTCP通信程序三次握手和四次挥手 来源Gitee地址 网络编程三要素 IP: 设备在网络中的地址&#xff0c;是唯一的标识端口号: 应用程序在设备中唯一的标识。协议: 数据在…

2023OpenFeign源码

原理-源码 让我们看着源~码~ 按顺序走~趟流~程~ 分为两大部分&#xff1a;启动原理、调用流程 Feign 的Java 代码才 3w 多行&#xff0c;放眼现在热门的开源项目&#xff0c; Dubbo、Naocs、Skywalking 中 Java 代码都要 30w 行起步。 重要通知&#xff01;看源码&#xff0c;…

Winform制作的用户界面在高DPI下缩放问题

引言 熟悉Winform的小伙伴应该都遇到过 在100%缩放下制作的用户界面在其他缩放百分比下会出现字体超出边框的情况&#xff0c;导致用户体验大打折扣。用户程序DPI感知是默认打开的&#xff0c;此时可以通过关闭这种感知来禁用字体的缩放&#xff0c;在这种情况下&#xff0c;用…

C语言指针详解

目录 指针是什么? 指针和指针类型 指针-整数 指针的解引用 野指针 野指针成因 如何规避野指针 指针运算 指针- 整数 指针-指针 指针的关系运算 指针和数组 二级指针 指针数组 指针数组 模拟二维数组 指针是什么? 指针理解的2个要点: 1. 指针是内存中一个…

51单片机——串行口通信

目录 1、51单片机串口通信介绍 2、串行口相关寄存器 2.1 、串行口控制寄存器SCON和PCON 2.1.1 SCON&#xff1a;串行控制寄存器 (可位寻址) 2.1.2 PCON&#xff1a;电源控制寄存器&#xff08;不可位寻址&#xff09; 2.2、串行口数据缓冲寄存器SBUF 2.3、从机地址控制…

iOS - 解压ipa包中的Assert.car文件

项目在 Archive 打包后&#xff0c;生成ipa包 将 xxx.ipa文件修改为zip后缀即 xxx.zip &#xff0c;然后再双击解压&#xff0c;会生成一个 Payload 文件夹&#xff0c;里面一个文件 如下图&#xff1a; 然后显示改文件的包内容&#xff1a; 解压 Assets.car 文件的方式&…

基于x-scan的渲染算法

基于x-scan算法实现的z-buffer染色&#xff0c;.net core framework 3.1运行。 x-scan算法实现&#xff1a; public List<Vertex3> xscan() {List<Vertex3> results new List<Vertex3>();SurfaceFormula formula getFormula();Box rect getBound();for …

力扣 968. 监控二叉树

题目来源&#xff1a;https://leetcode.cn/problems/binary-tree-cameras/description/ C题解&#xff08;来源代码随想录&#xff09;&#xff1a;节点可以分为3个状态&#xff1a;0无覆盖&#xff1b;1有摄像头&#xff1b;2有覆盖。 要想放的摄像头最少&#xff0c;应当叶子…

无涯教程-jQuery - stop( clearQueue, gotoEnd)方法函数

stop([clearQueue&#xff0c;gotoEnd])方法停止所有指定元素上的所有当前正在运行的动画。 stop( [clearQueue, gotoEnd ]) - 语法 selector.stop( [clearQueue], [gotoEnd] ) ; 这是此方法使用的所有参数的描述- clearQueue - 这是可选的布尔参数。设置为true会清除动画…

绕过TLS/akamai指纹护盾

文章目录 前言TLS指纹什么是TLS指纹测试TLS指纹绕过TLS指纹使用原生urllib使用其他成熟库&#xff01;&#xff01;修改requests底层代码 Akamai指纹相关&#xff08;HTTP/2指纹&#xff09;什么是Akamai指纹测试Akamai指纹绕过Akamai指纹使用其他成熟库 实操参考 前言 有道是…

Eureka 学习笔记3:EurekaHttpClient

版本 awsVersion ‘1.11.277’ EurekaTransport 用于客户端和服务端之间进行通信&#xff0c;封装了以下接口的实现&#xff1a; ClosableResolver 接口实现TransportClientFactory 接口实现EurekaHttpClient 接口实现及其对应的 EurekaHttpClientFactory 接口实现 private …

【雕爷学编程】MicroPython动手做(16)——掌控板之图片图像显示2

知识点&#xff1a;什么是掌控板&#xff1f; 掌控板是一块普及STEAM创客教育、人工智能教育、机器人编程教育的开源智能硬件。它集成ESP-32高性能双核芯片&#xff0c;支持WiFi和蓝牙双模通信&#xff0c;可作为物联网节点&#xff0c;实现物联网应用。同时掌控板上集成了OLED…

第120天:免杀对抗-防朔源防流量防特征CDN节点SSL证书OSS存储上线

知识点 #知识点&#xff1a; 1、CS-CDN节点-防拉黑 2、CS-SSL证书-防特征 3、CS-OSS存储-防流量#章节点&#xff1a; 编译代码面-ShellCode-混淆 编译代码面-编辑执行器-编写 编译代码面-分离加载器-编写 程序文件面-特征码定位-修改 程序文件面-加壳花指令-资源 代码加载面-D…

springCloud Eureka注册中心配置详解

1、创建一个springBoot项目 2、在springBoot项目中添加SpringCloud依赖 <dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-dependencies</artifactId><version>2021.0.3</version><type>…

IDEA 使用 maven 搭建 spring mvc

1. 创建项目 1.1 创建成功之后配置 Spring MVC 1.2 勾选 Spring MVC 2.更改配置文件 2.1 更改web.xml配置 更改为 <servlet-mapping><servlet-name>dispatcher</servlet-name><url-pattern>/</url-pattern></servlet-mapping>2.2 dispat…

CF1833 A-E

A题 题目链接&#xff1a;https://codeforces.com/problemset/problem/1833/A 基本思路&#xff1a;for循环遍历字符串s&#xff0c;依次截取字符串s的子串str&#xff0c;并保存到集合中&#xff0c;最后输出集合内元素的数目即可 AC代码&#xff1a; #include <iostrea…

Michael.W基于Foundry精读Openzeppelin第15期——SignedMath.sol

Michael.W基于Foundry精读Openzeppelin第15期——SignedMath.sol 0. 版本0.1 SignedMath.sol 1. 目标合约2. 代码精读2.1 max(int256 a, int256 b) && min(int256 a, int256 b)2.2 average(int256 a, int256 b)2.3 abs(int256 n) 0. 版本 [openzeppelin]&#xff1a;v…

final的使用以及权限修饰符

final表示最终的、不可改变的 final跟abstract不可以同时使用&#xff0c;因为二者是冲突的。final表示不可变&#xff0c;abstrac表示必须要重写、必须要变。 常见的四种用法 修饰一个类 格式&#xff1a; public final class 类名称{ }final修饰之后&#xff0c;这个类不能…