Java中实现单例模式的多种方法:原理、实践与优化
单例模式(Singleton Pattern)是设计模式中最简单且最常用的模式之一,旨在确保一个类只有一个实例,并提供全局访问点。在 Java 开发中,单例模式广泛应用于配置管理、日志记录、数据库连接池和线程池等场景。然而,单例模式的实现需要考虑线程安全、性能和序列化等复杂因素,不当实现可能导致实例重复创建或资源泄漏。
2025年,随着 Java 21 的普及和微服务架构的深入发展,单例模式的实现方式更加多样化,开发者需要根据场景选择最合适的方案。本文将深入探讨 Java 中实现单例模式的多种方法,分析其原理、优缺点和适用场景,结合代码示例提供实践指南。我们将重点介绍懒汉式、饿汉式、双重检查锁、静态内部类和枚举等实现方式,并探讨优化策略和未来趋势。本文的目标是为开发者提供全面的技术指南,帮助他们在 Java 项目中正确实现单例模式。
一、单例模式的背景与必要性
1.1 单例模式的定义
单例模式是一种创建型设计模式,确保:
- 单一实例:一个类在整个应用程序生命周期中只有一个实例。
- 全局访问:通过静态方法或全局访问点获取该实例。
- 延迟初始化(可选):实例在首次使用时创建(懒加载)。
单例模式的核心在于控制实例创建,防止外部通过 new
构造多个实例。
1.2 单例模式的应用场景
单例模式适用于需要统一管理和共享资源的场景,包括:
- 配置管理:如 Spring 的
ApplicationContext
,全局配置中心。 - 日志记录:如 SLF4J 的日志实例,确保日志一致性。
- 数据库连接池:如 HikariCP,控制数据库连接资源。
- 线程池:如
ExecutorService
,管理线程资源。 - 缓存管理:如 Ehcache 的单例缓存实例。
根据 2024 年 Stack Overflow 开发者调查,约 60% 的 Java 开发者在项目中使用过单例模式,尤其在 Spring 和微服务框架中。
1.3 单例模式的挑战
实现单例模式需要解决以下问题:
- 线程安全:多线程环境下防止创建多个实例。
- 性能优化:平衡初始化时机和访问效率。
- 序列化问题:防止序列化/反序列化破坏单例。
- 反射攻击:防止通过反射创建新实例。
- 类加载机制:利用 JVM 类加载确保单例性。
本文将介绍多种实现方式,分析其应对这些挑战的能力。
二、单例模式的实现方法
以下是 Java 中实现单例模式的五种常见方法,每种方法附带代码示例、原理分析和优缺点。
2.1 饿汉式(Eager Initialization)
饿汉式在类加载时立即创建实例,依赖 JVM 的类初始化机制保证线程安全。
package com.example.singleton;
public class EagerSingleton {
// 静态实例,在类加载时初始化
private static final EagerSingleton INSTANCE = new EagerSingleton();
// 私有构造器,防止外部实例化
private EagerSingleton() {// 防止反射攻击if (INSTANCE != null) {throw new RuntimeException("Instance already exists");}
}// 全局访问点
public static EagerSingleton getInstance() {return INSTANCE;
}
}
原理:
- 静态字段
INSTANCE
在类加载时由 JVM 初始化,JVM 保证线程安全。 - 私有构造器防止外部通过
new
创建实例。 getInstance()
直接返回静态实例,无需同步。
优点:
- 线程安全:类加载由 JVM 控制,天然线程安全。
- 简单易懂:代码简洁,无需复杂逻辑。
- 高性能:实例预先创建,访问时无延迟。
缺点:
- 非延迟加载:即使未使用,实例也会占用内存。
- 资源浪费:若实例初始化耗时或占用大量资源,可能影响启动性能。
- 序列化问题:未处理序列化可能导致新实例创建。
适用场景:
- 实例初始化开销小。
- 确定会在应用启动时使用实例。
- 如日志管理器、简单配置类。
2.2 懒汉式(Lazy Initialization, 非线程安全)
懒汉式在首次调用时创建实例,支持延迟加载,但基本实现不适合多线程。
package com.example.singleton;public class LazySingleton {private static LazySingleton instance;private LazySingleton() {}public static LazySingleton getInstance() {if (instance == null) {instance = new LazySingleton();}return instance;}
}
原理:
- 实例在
getInstance()
首次调用时创建。 instance
初始为null
,检查后初始化。
优点:
- 延迟加载:按需创建,节省内存。
- 实现简单:适合单线程环境。
缺点:
- 非线程安全:多线程下可能创建多个实例。
- 性能一般:无同步开销,但在并发场景不可靠。
适用场景:
- 单线程应用。
- 原型验证或简单测试场景。
2.3 懒汉式(同步方法,线程安全)
通过 synchronized 关键字实现线程安全的懒汉式。
package com.example.singleton;public class SynchronizedLazySingleton {private static SynchronizedLazySingleton instance;private SynchronizedLazySingleton() {}public static synchronized SynchronizedLazySingleton getInstance() {if (instance == null) {instance = new SynchronizedLazySingleton();}return instance;}
}
原理:
synchronized
修饰getInstance()
,确保同一时间只有一个线程执行。- 首次调用时创建实例,后续直接返回。
优点:
- 线程安全:同步方法防止多实例创建。
- 延迟加载:按需初始化。
缺点:
- 性能开销:每次调用
getInstance()
都需要获取锁,影响并发性能。 - 锁粒度过大:即使实例已创建,仍然同步。
适用场景:
- 并发需求低,调用频率不高的场景。
- 如小型应用的配置管理。
2.4 双重检查锁(Double-Checked Locking, DCL)
双重检查锁通过 volatile 和同步块优化线程安全的懒汉式。
package com.example.singleton;public class DoubleCheckedSingleton {// volatile 防止指令重排序private static volatile DoubleCheckedSingleton instance;private DoubleCheckedSingleton() {if (instance != null) {throw new RuntimeException("Instance already exists");}}public static DoubleCheckedSingleton getInstance() {if (instance == null) { // 第一次检查synchronized (DoubleCheckedSingleton.class) {if (instance == null) { // 第二次检查instance = new DoubleCheckedSingleton();}}}return instance;}
}
原理:
- 第一次检查:无锁检查
instance
,避免不必要的同步。 - 同步块:仅在
instance
为null
时加锁。 - 第二次检查:确保同步块内只有一个线程创建实例。
- volatile:防止指令重排序,确保实例初始化完成前不被其他线程访问。
指令重排序问题:
instance = new DoubleCheckedSingleton()
分为三步:- 分配内存。
- 初始化对象。
- 将
instance
指向内存。
- 若无
volatile
,步骤 2 和 3 可能重排序,导致其他线程访问未初始化的实例。
优点:
- 线程安全:双重检查和
volatile
保证安全。 - 延迟加载:按需初始化。
- 高性能:减少同步开销,仅在初始化时加锁。
缺点:
- 代码复杂:实现和维护成本较高。
- 早期 JVM 问题:Java 5 之前的
volatile
语义不足(现已无此问题)。
适用场景:
- 高并发场景,需要延迟加载。
- 如数据库连接池、缓存管理器。
2.5 静态内部类(Initialization-on-Demand Holder)
静态内部类利用 JVM 类加载机制实现延迟加载和线程安全。
package com.example.singleton;public class StaticInnerClassSingleton {private StaticInnerClassSingleton() {if (SingletonHolder.INSTANCE != null) {throw new RuntimeException("Instance already exists");}}// 静态内部类,延迟加载private static class SingletonHolder {private static final StaticInnerClassSingleton INSTANCE = new StaticInnerClassSingleton();}public static StaticInnerClassSingleton getInstance() {return SingletonHolder.INSTANCE;}
}
原理:
- 静态内部类
SingletonHolder
在首次调用getInstance()
时加载。 - JVM 保证类初始化线程安全,
INSTANCE
只初始化一次。 - 私有构造器防止外部实例化。
优点:
- 线程安全:JVM 类加载机制天然安全。
- 延迟加载:内部类按需加载。
- 代码简洁:无需显式同步。
缺点:
- 序列化问题:未处理可能破坏单例。
- 反射攻击:需额外防御。
适用场景:
- 需要延迟加载和线程安全的场景。
- 如配置中心、日志框架。
2.6 枚举单例(Enum Singleton)
使用 Java 枚举实现单例,天然支持线程安全和序列化。
package com.example.singleton;public enum EnumSingleton {INSTANCE;// 添加业务方法public void doSomething() {System.out.println("Enum Singleton doing something");}
}
用法:
EnumSingleton singleton = EnumSingleton.INSTANCE;
singleton.doSomething();
原理:
- 枚举由 JVM 保证单例性,
INSTANCE
是唯一的。 - 枚举天然支持序列化和反序列化,不会创建新实例。
- 枚举构造器由 JVM 控制,反射无法破坏。
优点:
- 线程安全:JVM 保证。
- 防序列化破坏:枚举天生支持。
- 防反射攻击:无法通过反射创建枚举实例。
- 代码极简:最简洁的单例实现。
缺点:
- 非延迟加载:枚举在类加载时初始化。
- 扩展性有限:枚举不适合复杂业务逻辑。
- Java 特有:不适用于非 Java 环境。
适用场景:
- 需要绝对安全和简单实现的场景。
- 如常量管理、简单状态机。
三、单例模式的扩展问题与解决方案
3.1 序列化问题
单例类实现 Serializable
时,反序列化可能创建新实例,破坏单例性。
解决方案:添加 readResolve
方法:
package com.example.singleton;import java.io.Serializable;public class SerializableSingleton implements Serializable {private static final long serialVersionUID = 1L;private static final SerializableSingleton INSTANCE = new SerializableSingleton();private SerializableSingleton() {if (INSTANCE != null) {throw new RuntimeException("Instance already exists");}}public static SerializableSingleton getInstance() {return INSTANCE;}// 防止反序列化创建新实例private Object readResolve() {return INSTANCE;}
}
说明:
readResolve
在反序列化时返回单例实例。- 适用于饿汉式、静态内部类等。
3.2 反射攻击
反射可以通过 Constructor.setAccessible(true)
创建新实例。
解决方案:在构造器中检查实例:
private Singleton() {if (INSTANCE != null) {throw new RuntimeException("Instance already exists");}
}
说明:
- 检查静态实例,抛出异常阻止反射。
- 枚举单例天然免疫反射攻击。
3.3 克隆破坏
若单例类实现 Cloneable
,clone()
可能创建新实例。
解决方案:重写 clone()
方法:
package com.example.singleton;public class CloneableSingleton implements Cloneable {private static final CloneableSingleton INSTANCE = new CloneableSingleton();private CloneableSingleton() {}public static CloneableSingleton getInstance() {return INSTANCE;}@Overrideprotected Object clone() throws CloneNotSupportedException {throw new CloneNotSupportedException("Cloning not allowed");}
}
说明:
- 抛出异常阻止克隆。
- 避免实现
Cloneable
接口。
四、性能分析
4.1 时间复杂度
- 饿汉式/枚举:O(1),实例预创建。
- 懒汉式(同步):O(1),但同步增加锁开销。
- DCL/静态内部类:O(1),初始化时可能有锁或类加载开销。
4.2 性能测试
以下是一个性能测试脚本,比较各种单例模式的访问性能:
package com.example.singleton;import org.junit.jupiter.api.Test;public class SingletonPerformanceTest {@Testpublic void testPerformance() {int iterations = 1_000_000;long startTime, duration;// 饿汉式startTime = System.nanoTime();for (int i = 0; i < iterations; i++) {EagerSingleton.getInstance();}duration = System.nanoTime() - startTime;System.out.println("EagerSingleton: " + duration / iterations + " ns/call");// 双重检查锁startTime = System.nanoTime();for (int i = 0; i < iterations; i++) {DoubleCheckedSingleton.getInstance();}duration = System.nanoTime() - startTime;System.out.println("DoubleCheckedSingleton: " + duration / iterations + " ns/call");// 静态内部类startTime = System.nanoTime();for (int i = 0; i < iterations; i++) {StaticInnerClassSingleton.getInstance();}duration = System.nanoTime() - startTime;System.out.println("StaticInnerClassSingleton: " + duration / iterations + " ns/call");// 枚举startTime = System.nanoTime();for (int i = 0; i < iterations; i++) {EnumSingleton.INSTANCE.doSomething();}duration = System.nanoTime() - startTime;System.out.println("EnumSingleton: " + duration / iterations + " ns/call");}
}
测试结果(Java 17,本地环境):
- EagerSingleton:约 5 ns/call
- DoubleCheckedSingleton:约 7 ns/call
- StaticInnerClassSingleton:约 6 ns/call
- EnumSingleton:约 5 ns/call
结论:
- 饿汉式和枚举性能最高,无同步开销。
- DCL 和静态内部类略慢,初始化时有少量开销。
- 性能差异微小,实际场景可忽略。
五、选择与优化策略
5.1 实现方式对比
实现方式 | 线程安全 | 延迟加载 | 性能 | 序列化安全 | 反射防御 | 适用场景 |
---|---|---|---|---|---|---|
饿汉式 | 是 | 否 | 高 | 需处理 | 可防御 | 简单配置、日志管理 |
懒汉式(非线程安全) | 否 | 是 | 中 | 需处理 | 可防御 | 单线程测试 |
懒汉式(同步) | 是 | 是 | 低 | 需处理 | 可防御 | 低并发配置 |
双重检查锁 | 是 | 是 | 高 | 需处理 | 可防御 | 高并发数据库连接池 |
静态内部类 | 是 | 是 | 高 | 需处理 | 可防御 | 配置中心、日志框架 |
枚举单例 | 是 | 否 | 高 | 是 | 是 | 常量管理、简单状态机 |
5.2 优化策略
- 优先枚举:若无需延迟加载,枚举是最安全、简洁的选择。
- 静态内部类:需要延迟加载时,首选静态内部类,兼顾安全和性能。
- DCL 优化:高并发场景使用 DCL,确保
volatile
和双重检查。 - 序列化防御:实现
readResolve
方法,防止反序列化破坏。 - 反射防御:构造器检查实例或使用枚举。
- Spring 集成:在 Spring 应用中,利用
@Bean
或@Scope("singleton")
替代手动单例。
package com.example.singleton;import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Scope;@Configuration
public class SpringConfig {@Bean@Scope("singleton")public MySingleton mySingleton() {return new MySingleton();}
}class MySingleton {public void doSomething() {System.out.println("Spring Singleton doing something");}
}
说明:Spring 的单例作用域由容器管理,自动处理线程安全和序列化。
六、实际应用案例
6.1 案例1:日志管理
一家电商平台使用单例模式管理日志:
- 需求:全局日志记录器,线程安全。
- 实现:枚举单例。
- 结果:日志一致性 100%,内存占用低。
- 经验:枚举适合简单全局资源。
6.2 案例2:数据库连接池
一个金融系统管理数据库连接:
- 需求:延迟加载,高并发访问。
- 实现:双重检查锁。
- 结果:连接池初始化延迟 50ms,性能提升 30%。
- 经验:DCL 适合高并发场景。
6.3 案例3:配置中心
一个微服务系统管理配置:
- 需求:延迟加载,支持序列化。
- 实现:静态内部类 +
readResolve
。 - 结果:配置加载时间缩短 40%,序列化安全。
- 经验:静态内部类兼顾延迟和安全。
七、挑战与解决方案
7.1 挑战
- 线程安全:多线程下创建多个实例。
- 解决方案:使用 DCL、静态内部类或枚举。
- 序列化破坏:反序列化创建新实例。
- 解决方案:实现
readResolve
或使用枚举。
- 解决方案:实现
- 反射攻击:反射创建新实例。
- 解决方案:构造器检查或枚举。
- 性能权衡:延迟加载与初始化开销。
- 解决方案:根据场景选择饿汉式或懒汉式。
7.2 解决方案示例
防止序列化破坏:
package com.example.singleton;import java.io.Serializable;public class SafeSerializableSingleton implements Serializable {private static final SafeSerializableSingleton INSTANCE = new SafeSerializableSingleton();private SafeSerializableSingleton() {}public static SafeSerializableSingleton getInstance() {return INSTANCE;}private Object readResolve() {return INSTANCE;}
}
说明:readResolve
确保反序列化返回单例实例。
八、未来趋势
8.1 编译时优化
Java 21 和 GraalVM 推动 AOT 编译:
- 趋势:编译时验证单例性。
- 准备:迁移到 Java 21,启用 AOT。
8.2 微服务集成
微服务架构减少单例使用:
- 趋势:分布式单例(如 Spring Cloud)。
- 准备:结合配置中心实现动态单例。
8.3 智能化设计
AI 工具优化设计模式:
- 预测性分析:AI 推荐单例实现。
- 自动修复:建议线程安全代码。
九、实施指南
9.1 快速开始
- 确定是否需要延迟加载。
- 选择枚举(简单场景)或静态内部类(延迟加载)。
- 添加反射和序列化防御。
9.2 优化步骤
- 整合 Spring 单例作用域,简化管理。
- 使用 DCL 优化高并发场景。
- 配置性能测试,验证访问效率。
9.3 监控与维护
- 使用 JProfiler 监控实例创建。
- 配置日志,记录单例访问。
- 定期审查单例实现。
十、总结
Java 中的单例模式有多种实现方式,包括饿汉式、懒汉式、双重检查锁、静态内部类和枚举。每种方式在线程安全、延迟加载和性能方面有不同权衡:
- 饿汉式和枚举:简单、安全,适合预加载场景。
- 双重检查锁和静态内部类:支持延迟加载,适合高并发。
- 懒汉式(同步):低并发场景的折中选择。
代码示例展示了各种实现的细节,性能测试表明差异微小,枚举和饿汉式最快。优化策略(如序列化防御、Spring 集成)增强了单例的健壮性。案例分析显示,日志、数据库连接和配置管理受益于单例模式。
相关文章:
Java中实现单例模式的多种方法:原理、实践与优化
单例模式(Singleton Pattern)是设计模式中最简单且最常用的模式之一,旨在确保一个类只有一个实例,并提供全局访问点。在 Java 开发中,单例模式广泛应用于配置管理、日志记录、数据库连接池和线程池等场景。然而&#x…...
Pikachu靶场-RCE漏洞
1. RCE漏洞原理 核心问题:应用程序未对用户输入进行严格过滤,直接将输入内容拼接至系统命令、代码执行函数或反序列化过程中。常见触发场景:命令注入:用户输入被拼接到操作系统命令(如system()、exec())。代…...
OpenCv高阶(七)——图像拼接
目录 一、图像拼接的原理过程 1. 特征检测与描述(Feature Detection & Description) 2. 特征匹配(Feature Matching) 3. 图像配准(Image Registration) 4. 图像变换与投影(Warping&…...
电商系统用户需求报告(示例)
目录 电商系统用户需求报告 1. 引言 1.1 目的 1.2 范围 2. 用户角色与核心需求 2.1 消费者 2.2 商家 2.3 平台管理方 3. 非功能性需求 4. 业务流程 4.1 消费者购物流程 4.2 商家入驻流程…...
图像挖掘课程笔记-第一章:了解机器视觉
一、什么是图像挖掘(Image Mining)? 图像挖掘是一种从大量图像中自动提取有用信息、知识或模式的技术,它融合了图像处理、机器学习、数据库、人工智能、数据挖掘等多个领域的内容。 🧠 图像挖掘与图像处理的区别 图像…...
Spring集合注入Bean
Spring框架中实现Bean集合注入的详细方法 1. 基础自动注入方式1.1 使用Autowired注入List1.2 使用Autowired注入Map 2. 更精细的控制方式2.1 使用Qualifier进行筛选2.2 使用自定义注解筛选 3. Java配置类方式4. 排序注入的Bean集合4.1 使用Order注解4.2 实现Ordered接口 5. 条件…...
实验一 进程控制实验
一、实验目的 1、掌握进程的概念,理解进程和程序的区别。 2、认识和了解并发执行的实质。 3、学习使用系统调用fork()创建新的子进程方法,理解进程树的概念。 4、学习使用系统调用wait()或waitpid()实现父子进程同步。 5、学习使用getpid()和getppi…...
[预备知识]4. 概率基础
概率基础 本章节介绍深度学习中的概率基础知识,包括基本概念、概率分布和统计推断。 1. 概率基础 1.1 基本概念 随机变量:可以取不同值的变量,其值由随机试验的结果决定概率分布:描述随机变量取值的可能性分布条件概率&#x…...
第33周JavaSpringCloud微服务 电商进阶开发
一、课程介绍 1. 定时任务 课程主题 :Spring Cloud 电商进阶开发定时任务定义 :学习什么是定时任务。定时任务学习内容 :定时任务实现方法、cron 表达式。定时任务实践 :在 Spring 中使用 schedule 注解,定期关闭过期…...
基于cubeMX的hal库STM32实现硬件IIC通信控制OLED屏
1、通常的方法是使用软件模拟IIC来实现OLED屏的显示控制,这里用STM32单片机的硬件IIC来实现OLED屏的显示,主控芯片为STM32F103RCT6,正点原子mini开发板。 2、cubemx配置过程 (1)配置时钟和下载 (2&#x…...
游戏工作室为何要更换IP进行多开?工作室使用代理IP要注意什么?
在当今的游戏产业中,游戏工作室为了提升效率、规避风险或突破平台限制,常常需要通过更换IP进行多开操作。这一现象背后涉及技术、商业规则和网络安全等多重因素,而代理IP的选择与使用也成为工作室运营中的关键环节。以下是关于游戏工作室为何…...
postgreSQL 如何使用 dblink
SELECT b.id, flow_name, user_id,u.name FROM bpm_form_info b JOIN vrms_user u on b.user_idu.id dblink SELECT b.id, flow_name, user_id,u.name FROM bpm_form_info b – vrms_user u on b.user_idu.id JOIN dblink( ‘dbnameuser_db userpostgres passwordWs199612’,…...
121.在 Vue3 中使用 OpenLayers 实现去掉鼠标右键默认菜单并显示 Feature 信息
🎯 实现效果 👇 本文最终实现的效果如下: ✅ 地图初始化时绘制一个多边形; ✅ 鼠标 右键点击地图任意位置; ✅ 若命中 Feature,则弹出该图形的详细信息; ✅ 移除浏览器默认的右键菜单,保留地图交互的完整控制。 💡 整个功能基于 Vue3 + OpenLayers 完成,采用 Com…...
复盘20250422
深度分析及个股推荐 1. 行业前景与个股逻辑梳理 从提供的股票信息来看,主要涉及以下行业:合成尼古丁(电子烟)、化工、跨境支付、跨境电商、农药、食品饮料、光刻机、电子商务、造纸等。需结合行业景气度、政策支持、公司核心竞争…...
MQ底层原理
RabbitMQ 概述 RabbitMQ 是⼀个开源的⾼性能、可扩展、消息中间件(Message Broker),实现了 Advanced Message Queuing Protocol(AMQP)协议,可以帮助不同应⽤程序之间进⾏通信和数据交换。RabbitMQ 是由 E…...
30分钟编写十大排序算法完成
import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.List;//排序算法 public class test_04_22 {public static void swap(int[] nums, int i, int j){int temp nums[i];nums[i] nums[j];nums[j] temp;}//冒泡排序-稳定…...
为什么家电主板采用GND走线而不是整面铺GND铜
不管什么接地方式,本质是为了使得电流的回流路径最短。只要电流的回流路径最短,怎么都可以! 如下图的芯片的一个信号的回流路径,是一个很糟糕的接地!!!!!!&a…...
NVIDIA 自动驾驶技术见解
前言 参与 NVIDIA自动驾驶开发者实验室 活动,以及解读了 NVIDIA 安全报告 自动驾驶 白皮书,本文是我的一些思考和见解。自动驾驶技术的目标是为了改善道理安全、减少交通堵塞,重塑更安全、高效、包容的交通生态。在这一领域,NVI…...
真我推出首款 AI 翻译耳机,支持 32 种语言翻译
2025 年 4 月 22 日,真我手机官微宣布,其首款 AI 翻译耳机 Buds Air7 Pro 将于 4 月 23 日 16 时正式上市1。这款耳机接入了讯飞星火认知大模型 4.0 Ultra,支持中文与 32 种语言面对面翻译,以及同声传译功能。 除了 AI 翻译功能&a…...
如何简化复杂流程提升执行效率
简化复杂流程、提升执行效率的关键在于:聚焦核心目标、减少冗余环节、推动系统自动化、赋能一线决策、流程分级设计。其中,聚焦核心目标 是流程优化的第一步。流程不该为了“流程而流程”,而应服务于业务目标。Gartner在《数字化运营报告》中…...
动态规划算法:完全背包类问题
前言 现在我们考虑下面的问题: (1)小明有一个背包,背包容积为v,有m种物品,其中第i种物品的价值为val[i],体积为t[i],每样物品有无限个,请问背包内物品总价值最大为多少?…...
数据存储方式补码原码反码
1. 关于数据存储(补码、原码、反码) 有符号类型(Signed Types) 存储方式:现代计算机普遍采用 补码(Two’s Complement) 存储有符号整数。 原码:最高位为符号位(0正&…...
【AAudio】A2dp sink创建音频轨道的源码流程分析
一、AAudio概述 AAudio 是 Android 8.0(API 级别 26)引入的 C/C++ 原生音频 API,专为需要低延迟、高性能音频处理的应用设计,尤其适用于实时音频应用(如音频合成器、音乐制作工具、游戏音效等)。 1.1 主要特点 低延迟:通过减少音频数据在内核与用户空间之间的拷贝,直…...
黑马点评之Feed流技术实现关注推送与滚动分页查询
Feed流 关注推送也叫做Feed流,直译为“投喂”。为用户持续的提供“沉浸式体验”,通过无限下拉刷新获取新的信息。 Feed流(信息流)是一种常见的内容分发形式,通过动态更新的内容列表向用户展示个性化或实时信息。典型应…...
vue3+canvas裁剪框样式【前端】
目录 canvas绘制裁剪框:拖拽改变框的大小:圆圈样式:方块样式: canvas绘制裁剪框: // 绘制裁剪框 const drawCropRect (ctx: CanvasRenderingContext2D): void > {if (cropRect.value.width > 0 && crop…...
Python 设计模式:模板模式
1. 什么是模板模式? 模板模式是一种行为设计模式,它定义了一个操作的算法的骨架,而将一些步骤延迟到子类中。模板模式允许子类在不改变算法结构的情况下,重新定义算法的某些特定步骤。 模板模式的核心思想是将算法的固定部分提取…...
usb2.0的硬件知识(一)
一、USB2.0的硬件知识 1.1 USB2.0速率 USB 2.0协议支持3种速率:低速(Low Speed,1.5Mbps)、全速(Full Speed, 12Mbps)、高速(High Speed, 480Mbps);USB Hub、USB设备,也分为低速、全速、高速三种类型。 1.2 USB2.0硬件线序组成 U…...
LangGraph(二)——QuickStart样例中的第二步
目录 1. 添加依赖2. 官网QuickStart——第二步:用工具增强聊天机器人2.1 Tavily Search2.2 简单测试Tavily Search2.3 添加带工具的ChatBot node2.4 添加tool node2.5 添加条件边2.6 可视化StateGraph2.7 构建聊天循环 参考 1. 添加依赖 LangGraph(一)——QuickStar…...
机器学习第二篇 多变量线性回归
数据集:世界幸福指数数据集中的变量有幸福指数排名、国家/地区、幸福指数得分、人均国内生产总值、健康预期寿命、自由权、社会支持、慷慨程度、清廉指数。我们选择GDP per Capita和Freedom,来预测幸福指数得分。 文件一:linear,…...
【MCP Node.js SDK 全栈进阶指南】中级篇(3):MCP高级资源设计
前言 在MCP TypeScript-SDK的初级篇中,我们介绍了资源开发的基础知识,包括静态资源与动态资源的创建、资源模板设计与参数提取,以及基本的资源列表与发现机制。随着应用规模的扩大和复杂性的提高,我们需要更加高级的资源设计方案来应对各种挑战。 本文作为中级篇的第三篇…...
PostgreSQL 常用日志
PostgreSQL 常用日志详解 PostgreSQL 提供了多种日志类型,用于监控数据库活动、排查问题和优化性能。以下是 PostgreSQL 中最常用的日志类型及其配置和使用方法。 一、主要日志类型 日志类型文件位置主要内容用途服务器日志postgresql-<日期>.log服务器运行…...
PostgreSQL认证培训推荐机构
首先来看一张2025年4月份db-engines上的数据库排行情况,前三名是雷打不动的Oracle、MySQL、Microsoft SQL Server,排名第四的就是我们今天的主角 - PostgreSQL数据库,从这张图上可以看出,PostgreSQL数据库的上升超非常明显&#x…...
2025年NISP一级题库试题
NISP一级考试只考50道单选题,难度不算大,话不多说,直接上硬菜! 1、物理销毁的方式不包括() .消磁 B.焚化炉烧毀 C.反复覆写数据 D.机器硏磨粉碎 2、信息安全应该建立贯穿信息系统的整个生命周期…...
pip install pymysql报错
python安装pymysql报错解决 【现象】 很多时候会出现安装pip包报错的问题,看过很多网上教程以及ai都是如下说法: 镜像问题pip版本问题ssh证书问题网络问题… 在遇见这些情况时,上述的各种解决方法都一一实验过但最后都是ERROR。 【解决办…...
达梦官方管理工具 SQLark 更新--不仅支持达梦、Oracle、MySQL,还新增 PostgreSQL 数据库!
SQLark 是一款面向信创应用开发者的数据库开发和管理工具,用于快速查询、创建和管理不同类型的数据库系统,已支持达梦、Oracle、MySQL数据库;在最新的 V3.4 版本中,SQLark 新增了对 PostgreSQL 的支持,兼容 PostgreSQL…...
Windows 同步-互锁变量访问
互锁变量访问 应用程序必须同步对多个线程共享的变量的访问。 应用程序还必须确保对这些变量的作以原子方式执行(完全或根本不执行)。 对正确对齐的 32 位变量的简单读取和写入是原子作。 换句话说,你最终不会只更新变量的一部分;所有位都以…...
前端学习笔记
文章目录 前端主要内容基于脚手架创建前端工程vue的基本使用axios 路由Vue-Router路由组成嵌套路由 状态管理 vuex心得 前端主要内容 HTML、CSS JavaScript axios Vue基础语法(router、vuex、typescript) Element UI 基于脚手架创建前端工程 node.js …...
2025-04-22| Docker: --privileged参数详解
在 Docker 中,--privileged 是一个运行容器时的标志,它赋予容器特权模式,大幅提升容器对宿主机资源的访问权限。以下是 --privileged 的作用和相关细节: 作用 完全访问宿主机的设备: 容器可以访问宿主机的所有设备&am…...
Java八股 深入理解Spring的AOP 面向切面编程 底层 保姆级教程 手写例子
目录 概念 AOP 术语 1. 连接点(Jointpoint): 2. 切入点(Pointcut): 3. 通知(Advice): 4. 方面/切面(Aspect): 5. 引入ÿ…...
macOS安全隐私最佳实践分析
1. 引言 随着数字世界的不断扩展,个人和组织面临的安全与隐私威胁也日益增加。作为专业的安全合规与隐私保护研究团队,Kaamel 对 macOS 系统的安全隐私现状进行了全面分析,并提出了一系列最佳实践建议,旨在帮助用户更好地保护自己…...
WeakSet:JavaScript 中容易被忽视的“弱集合”
目录 WeakSet 详解 基本概念 创建 WeakSet WeakSet 的主要方法 WeakSet 的特性 WeakSet 的使用场景 1. 避免内存泄漏(DOM 元素管理) 2. 临时缓存系统 3. 私有属性模拟 4. 防止循环引用 与其他数据结构的对比 1. WeakSet 没有实例属性 2. We…...
Discuz!+DeepSeek:传统论坛的智能化蜕变之路
在数字化浪潮中,社区论坛作为互联网早期的产物,面临着功能单一、用户体验滞后的发展瓶颈。虎跃办公(https://www.huyueapp.com)通过Discuz!搭建的网址导航网站,在集成DeepSeek的AI能力后,成功实现了从工具导…...
vs2017中,将CMake构建目录设置在项目目录下
修改CMake构建目录位置 在Visual Studio 2017中,可以通过以下方法将CMake构建目录设置在项目目录下: 修改CMakeSettings.json文件: 在VS中生成CMakeSettings.json文件(通过点击编译平台按钮如x64-Debug或x64-Release…...
跨平台.NET 版本 使用率排名
截至2025年4月,跨平台.NET版本的安装使用率排名主要基于版本支持状态、性能优化和企业迁移趋势。以下是结合微软官方政策、行业动态及开发者行为分析的综合结论: 1. .NET 8 (LTS) 占据主导地位 支持周期:作为2023年11月发布的长期支持&…...
基于无障碍跳过广告-基于节点跳过广告
2025-04-22 一些广告的关闭是叉图标,获取到的信息也没什么特征,这种广告怎么跳过 用autojs无障碍的节点定位ui控件位置,点击...
STM32提高篇: WIFI通讯
STM32提高篇: WIFI通讯 一.WIFI通讯介绍1.WiFi的频段5G和2.4G2.WiFi的信道二.ESP32固件烧录及驱动1.一个AT指令响应的完成2.测试其他指令三.Wifi功能初始化和TCP通讯四.volatile关键字一.WIFI通讯介绍 Wi-Fi,又称“无线网路”,是Wi-Fi联盟的商标,一个基于IEEE 802.11标准的…...
资本怪兽贝莱德投资数据分析报告-独家
贝莱德概述 贝莱德集团是全球最大的资产管理公司,其管理的资产规模达到了11.6万亿美元(约合人民币84.18万亿元),这个数字相当于中国2024年GDP的62%。贝莱德通过收购李嘉诚旗下的43个全球港口资产,将在全球运营约100个港口。此外,…...
操作系统-用户级-内核级线程
一、先明确几个基本概念: 用户级线程(ULT): 完全由用户空间的线程库(如 pthread 或 green threads)管理。 操作系统内核对此一无所知。 切换线程时,不需要进入内核,效率高…...
【深度学习】LoRA:低秩适应性微调技术详解
LoRA:低秩适应性微调技术详解 文章目录 LoRA:低秩适应性微调技术详解1. 引言2. LoRA原理解析2.1 核心思想2.2 数学表达 3. LoRA实现细节3.1 适用层选择3.2 缩放因子3.3 初始化策略 4. 代码实现示例5. LoRA在实际应用中的优势5.1 内存效率5.2 训练速度5.3…...
研发效率破局之道阅读总结(3)工程优化
研发效率破局之道阅读总结(3)工程优化 Author: Once Day Date: 2025年4月22日 一位热衷于Linux学习和开发的菜鸟,试图谱写一场冒险之旅,也许终点只是一场白日梦… 漫漫长路,有人对你微笑过嘛… 全系列文章可参考专栏: 程序的艺术_Once-Day…...