static 静态代码块在类加载时执行一次,适用于静态资源预加载、缓存/字典初始化及线程安全对象复用;需注意异常处理、初始化顺序及复杂场景下推荐使用@postconstruct等替代方案。

Java 中 static 静态代码块是类加载时自动执行的一次性初始化逻辑,适合用于静态资源的预加载——比如读取配置文件、初始化缓存、建立连接池或加载字典数据等。它在类第一次被主动使用(如创建实例、访问静态成员、反射调用等)前由 JVM 执行,且只执行一次,天然具备线程安全和单例保障特性。
静态代码块加载配置文件
当应用启动时需提前读取并解析 application.properties 或 JSON 配置,可将解析逻辑放入 static 块中,确保后续所有使用都基于已加载的数据:
- 用 ClassLoader.getResourceAsStream() 获取 classpath 下资源,避免路径硬编码
- 建议配合 try-with-resources 自动关闭流,防止资源泄漏
- 解析结果通常存入 static final 字段(如 Map
config),供全局只读访问
预热缓存或字典表
对于不常变更但查询频繁的业务数据(如省份列表、状态码映射),可在 static 块中从数据库或本地文件一次性加载到内存:
- 若依赖外部服务(如 DB),需考虑失败重试或降级策略,避免类加载失败导致整个类不可用
- 推荐将加载结果赋值给 static final 容器(如 Collections.unmodifiableMap),防止后续误修改
- 大型数据建议异步加载 + 标记就绪状态(如 volatile boolean loaded = false),避免阻塞类初始化
初始化线程安全的共享对象
像 SimpleDateFormat、Jackson ObjectMapper 等非线程安全但开销大的对象,适合在 static 块中构建为 static final 实例复用:
- 直接 new 出来赋值即可,JVM 保证初始化过程的原子性和可见性
- 避免在方法内重复创建,减少 GC 压力和对象分配开销
- 注意:不要在 static 块中调用尚未初始化的其他 static 字段(可能为 null),遵循声明顺序
注意事项与替代方案
static 块虽简洁,但调试困难、无法抛受检异常、不支持参数化,复杂场景建议更可控的方式:
- 不允许 throws 受检异常,必须用 try-catch 包裹并转为 RuntimeException
- 无法接收参数,不适合多环境差异化加载逻辑
- Spring 等框架中,优先使用 @PostConstruct 或 InitializingBean,便于单元测试和生命周期管理
- Java 9+ 可结合 ModuleSystem 的 static 初始化器,但主流仍以 static 块为主
不复杂但容易忽略细节,合理使用 static 块能让静态资源真正“一次加载、处处可用”。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











