Java Agent【java探针】及AspectJ

【JAVA基础☞探针技术】Java探针-Java Agent技术 我们利用javaAgent和ASM字节码技术,在JVM加载class二进制文件的时候,利用ASM动态的修改加载的class文件,在监控的方法前后添加计时器功能,用于计算监控方法耗时,同时将方法耗时及内部调用情况放入处理器,处理器利用栈先进后出的特点对方法调用先后顺序做处理,当一个请求处理结束后,将耗时方法轨迹和入参map输出到文件中,然后根据map中相应参数或耗时方法轨迹中的关键代码区分出我们要抓取的耗时业务。2、支持抓取特定的代码配置,方便对配置的特定方法进行抓取,过滤出关系的代码执行耗时情况。 阅读详情
AI摘要

本文介绍Java探针技术及AspectJ框架的应用,包括如何利用-javaagent参数在类加载前修改字节码,以及AspectJ如何实现面向切面编程。

在Java 语言中,织入切面分为:编译期织入(CTW: Compile-Time Weaving)、类加载期织入(LTW: Load-Time Weaving)和运行期织入(JDK代理和CGLIB)。编译期织入是指在Java编译期,将切面织入到类字节码中;而类加载期织入则指在类字节码加载到JVM时,织入切面;运行期织入则是采用CGLIB工具或JDK动态代理进行切面的织入。

什么是 Java Agent

Java Agent 又叫做 Java 探针,从JDK1.5 开始引入,可在类加载前修改class字节码。

Jvm启动参数 -javaagent 参数 俗称java探针技术(Premain方式)

使用方法:-javaagent:xxx.jar, 在main方法执行前查找jar中MANIFEST.MF文件的Premain-Class配置项,Premain-Class对应一个java类,然后执行方法premain(String options, Instrumentation instrumentation) 和premain(String options),如果同时存在,执行前者。

示例说明:

一个普通业务类:

package org.aop.service;

public class UserService {
    public void say() {
        System.out.println("Hello World!!");
    }
}

Premain-Class类:CustomPremainAgent,方法premain只执行一次

package org.aop.agent;

import java.lang.instrument.Instrumentation;

public class CustomPremainAgent {
    public static void premain(String agentArgs, Instrumentation inst) {
        if (inst == null) {
            throw new UnsupportedOperationException("JDK5才开始支持!!! preMain -javaagent");
        }

        System.out.println("Running==>premain(String agentArgs, Instrumentation inst)");
        System.out.println("agentArgs : " + agentArgs);

        //加入自定义转换器
        inst.addTransformer(new CustomClassFileTransformer(), true);
    }

    public static void premain(String agentArgs) {
        System.out.println("Running==>premain(String agentArgs)");
    }
}

Instrumentation:premain方法参数,由jvm虚拟机自动传入,class字节码载入jvm时触发执行transform方法(只执行一次)。

ClassFileTransformer类:CustomPremainAgent,拦截UserService类,利用javassist工具修改UserService的class字节码,修改say()方法添加切面功能

package org.aop.agent;

import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtMethod;

import java.lang.instrument.ClassFileTransformer;
import java.lang.instrument.IllegalClassFormatException;
import java.security.ProtectionDomain;

public class CustomClassFileTransformer implements ClassFileTransformer {

    @Override
    public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException {
        if (className.equals("org/aop/service/UserService")) {
            ClassPool classPool = ClassPool.getDefault();
            try {
                CtClass ctClass = classPool.get("org.aop.service.UserService");
                CtMethod ctMethod = ctClass.getDeclaredMethod("say");
                ctMethod.insertBefore("System.out.println(\"-javassist-- before say() ---\");");
                ctMethod.insertAfter("System.out.println(\"-javassist-- after say() ---\");");
                ctClass.detach();
                return ctClass.toBytecode();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        return new byte[0];
    }
}

MANIFEST.MF:在类路径META-INF下创建MANIFEST.MF文件

Manifest-Version: 1.0
Premain-Class: org.aop.agent.CustomPremainAgent
Can-Redefine-Classes: true
Can-Retransform-Classes: true
Class-Path: javassist-3.20.0-GA.jar
Build-Jdk-Spec: 1.8
Created-By: Maven Jar Plugin 3.2.0

然后将CustomPremainAgent.java、CustomClassFileTransformer.java、META-INF/MANIFEST.MF编译后打包.

如果用maven打包可以不用手动创建MANIFEST.MF文件

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <version>3.2.0</version>
    <configuration>
        <includes>
            <include>org/aop/agent/CustomPremainAgent.class</include>
            <include>org/aop/agent/CustomClassFileTransformer.class</include>
        </includes>
        <archive>
            <!--自动添加META-INF/MANIFEST.MF -->
            <manifest>
                <addClasspath>true</addClasspath>
            </manifest>
            <manifestEntries>
                <Premain-Class>org.aop.agent.CustomPremainAgent</Premain-Class>
                <Can-Redefine-Classes>true</Can-Redefine-Classes>
                <Can-Retransform-Classes>true</Can-Retransform-Classes>
            </manifestEntries>
        </archive>
    </configuration>
</plugin>

最后打包路径:D:/workspace/demo/target/user-service-agent.jar

测试代码:

public static void main(String[] args) {
    UserService service = new UserService();
    service.say();
}

在vm参数中加入:-javaagent:D:/workspace/demo/target/user-service-agent.jar

运行结果:

从JDK6开始,引入一种新的方式:Agentmain方式.
Premain只能在类加载之前修改字节码,类加载之后无能为力。而Agentmain恰恰可以弥补这缺点。Agentmain 可以在类加载之后再次加载这个类。

使用方法:VirtualMachine.loadAgent("XXX.jar", agentArgs), 在main方法执行中查找jar中MANIFEST.MF文件的Agent-Class配置项,Agent-Class对应一个java类,然后执行方法agentmain(String options, Instrumentation instrumentation) 和agentmain(String options),如果同时存在,执行前者。

示例说明:

Agent-Class类:CustomAgentmainAgent,方法agentmain只执行一次

package org.aop.agent;

import org.aop.service.UserService;

import java.lang.instrument.Instrumentation;

public class CustomAgentmainAgent {
    public static void agentmain(String agentArgs, Instrumentation inst) {
        if (inst == null) {
            throw new UnsupportedOperationException("JDK6才开始支持!!! agentmain -javaagent");
        }

        System.out.println("Running==>agentmain(String agentArgs, Instrumentation inst)");
        System.out.println("agentArgs : " + agentArgs);

        //加入自定义转换器
        inst.addTransformer(new CustomClassFileTransformer(), true);
        try {
            //允许修改字节码
            inst.retransformClasses(UserService.class);
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

    public static void agentmain(String agentArgs) {
        System.out.println("Running==>agentmain(String agentArgs)");
    }
}

MANIFEST.MF:在类路径META-INF下创建MANIFEST.MF文件

Manifest-Version: 1.0
Agent-Class: org.aop.agent.CustomAgentmainAgent
Can-Redefine-Classes: true
Can-Retransform-Classes: true
Class-Path: javassist-3.20.0-GA.jar
Build-Jdk-Spec: 1.8
Created-By: Maven Jar Plugin 3.2.0

然后将CustomAgentmainAgent .java、CustomClassFileTransformer.java、META-INF/MANIFEST.MF编译后打包.

最后打包路径:D:/workspace/demo/target/user-service-agent.jar

测试代码:

import com.sun.tools.attach.VirtualMachine;
import org.aop.service.UserService;

import java.lang.management.ManagementFactory;
import java.util.concurrent.TimeUnit;

public class AgentmainTest {
    public static void main(String[] args) throws Exception {
        taskThread.start();
        try {
            TimeUnit.SECONDS.sleep(10);
        } catch (Exception e) {
            e.printStackTrace();
        }

        String pid = jvmPid();
        System.out.println("进程pid==>" + pid);
        agent(pid);
    }

    /**
     * 获取jvm进程ID
     * 还可以通过jdk内置命令:jps -l 获取jvm进程ID
     * @return
     */
    private static String jvmPid() {
        String thisJvmName = ManagementFactory.getRuntimeMXBean().getName();
        String thisJvmPid = thisJvmName.split("@")[0];
        return thisJvmPid;
    }

    /**
     * 模拟运行中的系统
     */
    private static Thread taskThread =  new Thread() {
        @Override
        public void run() {
            while (true) {
                try {
                    TimeUnit.SECONDS.sleep(3);
                    UserService service = new UserService();
                    service.say();
                    System.out.println("\n");
                } catch (Exception e) {}
            }
        }
    };

    /**
     * agent attach
     *
     * @param pid
     */
    public static void agent(String pid) {
        try {
            System.out.println("=========准备增强类=========");
            VirtualMachine vm = VirtualMachine.attach(pid);
            vm.loadAgent("D:/workspace/demo/target/user-service-agent.jar", "org.aop.service.UserService");
            vm.detach();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
编译时,VirtualMachine可能无法编译,可以pom.xml添加如下依赖解决
<dependency>
    <groupId>jdk.tools</groupId>
    <artifactId>jdk.tools</artifactId>
    <version>1.8</version>
    <scope>system</scope>
    <!--<systemPath>${java.home}/lib/tools.jar</systemPath>-->
    <systemPath>C:/Program Files/Java/jdk-1.8/lib/tools.jar</systemPath>
</dependency>

运行结果:

什么是 AspectJ

AspectJ是一个面向切面的框架(AOP框架)。利用 -javaagent 实现的类加载期切面织入(LTW: Load-Time Weaving)

官网地址: Intro to AspectJ | Baeldung

源码地址:GitHub - eclipse-aspectj/aspectj

查看AspectJ jar包中的MANIFEST.MF可得知AspectJ的Premain-Class是 org.aspectj.weaver.loadtime.Agent

AspectJ从1.8.7版本开始支持Agentmain方式。

简单demo示例:

业务类:

package org.aop.service;

public class UserService {
    public void say() {
        System.out.println("Hello World!!");
    }
}

增强类:

package org.aop.aspectj;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;

@Aspect
public class AspectConfig {

	@Pointcut("execution(* org.aop.service..*.*(..))")
	public void callAt() {
	}

	@Around("callAt()")
	public Object around(ProceedingJoinPoint pjp) throws Throwable {
		System.out.println("Around==>before");
		Object object = pjp.proceed();
		System.out.println("Around==>after");
		return object;
	}

	public static AspectConfig aspectOf() {
		return new AspectConfig();
	}
}

META-INF新增aop.xml文件

<aspectj>
	<aspects>
		<aspect name="org.aop.aspectj.AspectConfig"/>
		<weaver options="-verbose -showWeaveInfo">
			<include within="org.aop.service.*"/>
		</weaver>
	</aspects>
</aspectj>

测试代码:

package org.aop;

import org.aop.service.UserService;

/*
  AspectJ官网地址:https://www.baeldung.com/aspectj

  在类路径META-INF下创建 aop.xml文件
  内容:
	<aspectj>
		<aspects>
			<aspect name="org.spring.aop.aspectj.AspectConfig"/>
			<weaver options="-verbose -showWeaveInfo">
				<include within="org.spring.aop.service.*"/>
			</weaver>
		</aspects>
	</aspectj>

  jvm启动参数:-javaagent:C:/Users/用户目录/.m2/repository/org/aspectj/aspectjweaver/1.7.4/aspectjweaver-1.7.4.jar
 */
public class AspectJMain {

	public static void main(String[] args) {
		UserService service = new UserService();
		service.say();
	}
}

执行测试:

   添加vm参数:-javaagent:XXXXX/aspectjweaver-1.7.4.jar

可以重写AspectJ的Premain-Class和ClassFileTransformer,将修改后的类字节码写入文件,查看生成情况。

package org.aop.agent;

import java.lang.instrument.ClassFileTransformer;
import java.lang.instrument.Instrumentation;

public class AspectAgent {
    /**
     * The instrumentation instance
     */
    private static Instrumentation s_instrumentation;

    /**
     * The ClassFileTransformer wrapping the weaver
     */
    private static ClassFileTransformer s_transformer = new ClassPreProcessorAgentAdapter();

    /**
     * JSR-163 preMain Agent entry method
     *
     * @param options
     * @param instrumentation
     */
    public static void premain(String options, Instrumentation instrumentation) {
        /* Handle duplicate agents */
        if (s_instrumentation != null) {
            return;
        }
        s_instrumentation = instrumentation;
        s_instrumentation.addTransformer(s_transformer);
    }

    /**
     * Returns the Instrumentation system level instance
     */
    public static Instrumentation getInstrumentation() {
        if (s_instrumentation == null) {
            throw new UnsupportedOperationException("Java 5 was not started with preMain -javaagent for AspectJ");
        }
        return s_instrumentation;
    }
}
package org.aop.agent;

import org.aspectj.weaver.loadtime.Aj;
import org.aspectj.weaver.loadtime.ClassPreProcessor;

import java.io.BufferedOutputStream;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.lang.instrument.ClassFileTransformer;
import java.nio.file.Files;
import java.nio.file.OpenOption;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.security.ProtectionDomain;

/**
 * Java 1.5 adapter for class pre processor
 *
 * @author <a href="mailto:alex@gnilux.com">Alexandre Vasseur</a>
 */
public class ClassPreProcessorAgentAdapter implements ClassFileTransformer {

    /**
     * Concrete preprocessor.
     */
    private static ClassPreProcessor s_preProcessor;

    static {
        try {
            s_preProcessor = new Aj();
            s_preProcessor.initialize();
        } catch (Exception e) {
            throw new ExceptionInInitializerError("could not initialize JSR163 preprocessor due to: " + e.toString());
        }
    }

    public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] bytes) {
        if (classBeingRedefined != null) {
            System.err.println("INFO: (Enh120375):  AspectJ attempting reweave of '" + className + "'");
        }
        byte[] newByte = s_preProcessor.preProcess(className, bytes, loader, protectionDomain);
        if (className.equals("org/aop/service/UserService")) { //写入文件
            this.writeFile(newByte);
        }
        return newByte;
    }

    //写入文件
    private void writeFile(byte[] newByte) {
        try {
            String dirPath = System.getProperty("user.dir") + "/src/proxy";
            Path outDirPath = Paths.get(dirPath);
            Files.createDirectories(outDirPath);
            Path outPath = Paths.get(dirPath + "/UserService$Proxy01.class");
            Files.write(outPath, newByte, new OpenOption[0]);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

记得重新生成MANIFEST.MF配置内容,重新打包,修改 -javaagent:XXX/自己的.jar.

WebLogic监控实战:AOP探针部署与性能指标采集深度解析 面向切面编程(AOP)是一种在程序运行时动态地将代码切入到指定方法或位置的编程范式,其核心原理是通过代理模式在不修改原有业务逻辑的前提下,实现横切关注点的模块化。在Java企业级应用监控领域,AOP技术被广泛应用于实现无侵入式的性能数据采集。其技术价值在于能够以极低开销自动捕获JVM、EJB、JDBC连接池等核心组件的运行时状态,为系统可观测性提供基础数据支撑。典型的应用场景包括对WebLogic、WebSphere等传统应用服务器的深度监控。本文聚焦于WebLogic Discovery Aspect这一 阅读详情

相关推荐

从模糊概念到完整方案:基于Java Agent与Flink构建实时追踪系统

在分布式系统与微服务架构中,实现应用性能监控与实时追踪是保障系统稳定性的关键技术。其核心原理在于通过无侵入式数据采集、高吞吐流处理与高效存储查询,构建端到端的可观测性链路。这项技术的价值在于能够实时洞察系统瓶颈、快速定位故障,并优化用户体验。典型的应用场景包括实时热点追踪、全链路性能分析以及高覆盖率热更新等。本文以“hot pursuit 100%”这一模糊目标为引,系统性地拆解了如何利用Java Agent实现无侵入埋点,结合Kafka与Flink构建实时流处理管道,并最终通过Elasticsearch与

weixin_33923762的博客 435

Java探针技术详解

Java探针技术详解

S1124654的博客 5081

深入理解Java Agent:让你的Java程序优雅地做“间谍”

Java Agent是一种特殊的Java程序,运行在目标Java应用前或运行时,用来修改目标应用的字节码。借助于Java Instrumentation API,Java Agent可以插入字节码转换,使得我们可以在不修改源代码的前提下就能够监控和增强程序的行为。Java Agent为我们提供了一种强大且灵活的机制,能够在不改变源码的情况下,实现对Java程序的监控、调试和增强。虽然它带来了很多便利,但也需要小心使用,以避免引入不必要的问题。

fudaihb的博客 2759

Java Agent 探针技术

Java Agent 直译为 Java 代理,也常常被称为 Java 探针技术。Java Agent 是在 JDK1.5 引入的,是一种可以动态修改 Java 字节码的技术。Java 中的类编译后形成字节码被 JVM 执行,在 JVM 在执行这些字节码之前获取这些字节码的信息,并且通过字节码转换器对这些字节码进行修改,以此来完成一些额外的功能。Java Agent 是一个不能独立运行 jar 包,它通过依附于目标程序的 JVM 进程,进行工作。

BASK2312的博客 3017

Java agent 使用详解

Java agent 使用详解

congge 8982

计算机组成原理 微程序控制器实验

微程序控制器实验 实验环境 计算机组成原理实验环境 实验目的 掌握微程序控制器的组成原理和工作过程。 理解微指令和微程序的概念,理解微指令与指令的区别与联系。 掌握指令操作码与控制存储器中微程序的对应方法。熟悉根据指令操作码从控制存储器中读出微程序的过程。 实验要求 做好实验预习,读懂实验电路图,熟悉实验元器件的功能特性和使用方法。 按照实验内容与步骤的要求,独立思考,认真仔细地完成实验。 写出实验报告。 实验电路        

Long_UP的博客 7万+

AspectJ和SpringAOP的区别

添加探针: 去C:\\*\.m2\repository\org\aspectj\aspect\aspectjweaver\版本号\aspectjweaver-版本号.jar。Agent这个类会帮我们注册一些属性,以后JVM在加载类的时候,会读取aop.xml文件,就知道了有哪些切面要织入到我们的这个类中。所以我们就用探针实现:AspectJ提供了探针,会在执行main之前,执行premain,即main方法的前置方法。AspectJ的本质是提供一种完全的OOP的编程范式,来实现三种时机的织入。

qq_74776071的博客 438

Web3前沿技术的智能合约安全审计

随着Web3技术的快速发展,智能合约作为区块链应用的核心组件,其安全性问题日益突出。本文旨在系统性地介绍智能合约安全审计的技术体系,帮助开发者理解智能合约安全风险,掌握安全审计的方法论和工具链。智能合约安全的基本概念常见漏洞类型及其原理安全审计的技术方法实际审计案例分析安全审计工具和资源首先介绍基本概念和背景然后分析常见漏洞和安全风险接着详细讲解安全审计技术提供实际案例和代码示例最后讨论工具资源和未来趋势智能合约:运行在区块链上的自执行程序,代码即法律安全审计。

AI天才研究院 1545

深入探讨Java Agent动态监控与字节码操作的力量

Java Agent是Java平台的一种机制,允许开发者在Java程序运行时插入代码以改变其行为。Java Agent通过Java Instrumentation API实现,可以在Java虚拟机启动时或运行时动态地修改类的字节码。这使得开发者能够进行监控、调试、分析和性能优化等多种操作,而无需修改源代码。Java Agent是一种特定的Java程序,可以在Java虚拟机(JVM)启动时或运行时附加到应用程序上。

hello.reader 1147

分享一个简单的迭代学习机器人双臂控制(MATLAB)

1 什么是迭代学习控制 迭代学习控制(iterative learning control,简称ILC)由Uchiyama于1978年首先提出,不过因为论文由日文撰写,影响不是很大。1984年,Arimoto等人用英文介绍了该方法。它是指不断重复一个同样轨迹的控制尝试,并以此修正控制律,以得到非常好的控制效果的控制方法。 迭代学习控制的特点是“在重复中学习”,通过反复的迭代修正,达到改善控制效果的目的。迭代学习控制的原理是根据系统前次运行所获得的输出误差信息,在控制过程中不断修正控制输入,随着迭代的进行,逐

weixin_45776027的博客 4483

Zemax:初学者的混合模式

光线以序列模式开始,然后接近非序列组件的入口端口。到达入口端口后,光线以非序列模式传播,然后接近出口端口。光线离开出口端口后,我们又回到序列模式。在此博客中,使用混合模式的示例将演示根据您自己的需要复制此工作流程所需的基本设置,以及一些有用的技巧。非序列组件表面类型必须在序列模式和非序列模式下定义。为了定义非序列组件的几何形状,请转到设置->编辑器->非序列,单击非序列编辑器。一旦我们进入非序列组件编辑器:表面 2 上的组件组,找到一个对象类型并进行定义。它能让您兼具序列模式的精确性和非序列模式的灵活性。

jkh920184196的博客 1337

Java 代码增强全套体系:代理、AOP、Agent、字节码

Java代码增强仅两种核心方案:包装式增强(如SpringAOP、动态代理,不改原字节码,生成代理类)与原地字节码增强(如AspectJ、JavaAgent,直接修改原类字节码)。SpringAOP借用AspectJ语法但底层为动态代理,存在this调用失效与切点限制;而AspectJ及Agent实现真正字节码级增强,支持静态方法、字段、构造器拦截,无代理缺陷。本质区别在于是否修改原类字节码。

长期深耕Java生态,聚焦微服务架构,分布式系统与企业级落地实践 367

ArcGIS+PLUS+InVEST三件套实战:从零搞定土地利用变化与碳储量预测(附完整数据包)

本文详细介绍了如何整合ArcGIS、PLUS模型和InVEST模型,构建土地利用变化与碳储量预测的完整研究流水线。通过多情景模拟和生态系统服务评估,提供从数据准备到结果验证的实战指南,助力研究者高效完成生态评估项目。

weixin_30399821的博客 541

aop的实现原理_非Spring管理Bean如何添加AOP呢?

前几天有个朋友问了一个问题,觉得可以给大家分享一下。问题如下图归其根本这是个历史项目,里面有很多的类并没有交给spring管理,但现在需要统一添加日志。面对这样的问题,其实只要了解AOP的原理,就会有多种方法。AOP都是基于动态代理来实现,而动态代理常见的就是cglib和java动态代理,不了解的可以看下之前干货君写的文章java动态代理为什么需要基于接口cglib动态代理对类没有任何限制吗?但此...

weixin_42350101的博客 3315

2026年CSP-J初赛真题及答案解析

2026年CSP-J初赛真题及题解

王老师青少年编程 1613

Node-RED教程(二):Node-RED的面板的操作

Node-RED系列(二):Node-RED的面板的操作 要使用Node-RED去搭建一个物联网平台,链接设备,设备通信,就必须要先熟悉Node-RED的这种面板,对于一个新的项目,在动手做之前一点想对这个的技术的文档有足够的了解做起来才能游刃有余。本期我给大家介绍一下Node-RED的各种面板,熟悉这些面板后,在后续的搭建Iot服务中,会举重若轻,同时该系列的文档,难度会逐步加深,知道了本章解释的名称后对后续文章的理解有很大帮助。 面板1:默认节点选项列表 安装Node-RED后默认的节点分为这5大类

知无涯 1万+

JavaAgent与IAST:运行时应用安全检测的探针机制

在应用安全测试领域,传统SAST与DAST分别受限于静态分析与外部视角,难以准确发现运行时才暴露的漏洞。IAST(交互式应用安全测试)通过将探针注入应用运行时,实时追踪污点数据流转,在敏感函数出口精准识别风险,显著降低误报漏报。其底层依赖JavaAgent字节码增强技术,在类加载阶段无缝织入检测逻辑,兼顾实时性与准确性。该方案适用于开发测试、生产监控及SDL流程中的安全卡点,尤其对Java生态的Web应用覆盖广泛。本文从IAST基本原理出发,拆解Agent架构、插桩点设计及污点上下文管理,并结合工程实践介绍

weixin_32247165的博客 212

全面解析量化价值投资多因子模型的原理

明明知道“买便宜的好公司”是价值投资的核心,但面对3000+只A股,如何快速筛选出“便宜又好”的标的?主观判断总被情绪干扰——明明PE很低的股票,买了却不涨;或者因为“感觉”错过牛股?想规模化投资,但手动分析100只股票就要花一周,根本无法覆盖全市场?量化价值投资的多因子模型,正是解决这些问题的钥匙。它将价值投资的核心逻辑(“便宜”“好公司”)转化为可量化的因子,用数学模型替代主观判断,实现系统化筛选、可回测验证、规模化复制的投资决策。为什么多因子模型能有效预测股票收益?

AI天才研究院 1056

Spring高级篇-AOP的4种实现方式底层原理

AOP 底层实现方式之一是代理,由代理结合通知和目标,提供增强功能。除此以外,aspectj 提供了两种另外的 AOP 底层实现 实现方式 底层原理 区别| ajc 编译器 通过 ajc 编译器在编译 class 类文件时,就把通知的增强功能,织入到目标类的字节码中 编译期间增强 agent探针 通过 agent 在加载目标类时,修改目标类的字节码,织入增强功能 加载期间通过ASM技术增强 jdk动态代理 jdk 动态代理要求目标必须实现接口,生成的代理类实现相同接口,因此代理与目标

dudu0917的博客 1120

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

Probability and Statistics - 4th edition

Probability and Statistics - 4th edition

Spring 核心技术解析【纯干货版】- Ⅶ:Spring 切面编程模块 Spring-Instrument 模块精讲

Spring-Instrument 模块,是 Spring 框架中一个用于提供类加载器增强和字节码操作支持的模块,主要围绕 类加载时织入(Load-Time Weaving, LTW) 提供功能。它是与 Spring AOP 和 Spring AspectJ 支持密切相关的模块之一,常被用于需要动态修改类行为的场景。

xht0832的博客 306

NTscan扫描工具

ntscan是一个扫描器,可以扫描没有密码和弱密码的共享,先到配置文件中填写猜测的用户名和密码,扫描过程中右侧出现的是扫描日志。

上一篇: Spring IOC 之 bean创建createBean()源码
下一篇: 修改final属性值-内联优化
java_key_code
博客等级 码龄16年 781粉丝 53原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值