compact constructor 是 record 中唯一能做前置校验的位置,必须在 this() 调用前完成空值、范围、格式等检查并抛出 illegalargumentexception 等运行时异常,否则字段已 final 初始化,校验失效。

Java 的 Record 类从 JDK 14(预览)到 JDK 16 正式引入,它天然不可变、自动生成 equals/hashCode/toString 和访问器方法。但默认构造逻辑无法校验字段——这时就要用 compact constructor(紧凑构造器)来插入自定义校验逻辑。
什么是 compact constructor
它是 Record 中唯一允许显式编写的构造器形式,语法简洁:不写参数列表、不写方法体花括号前的参数声明,直接写逻辑块。它在 record 字段初始化之后、对象完全构建之前执行,可用于对已赋值的组件字段做校验或标准化处理。
怎么写 compact constructor 做校验
在 record 声明体内直接写一个无参、无修饰符、无返回类型、名称与 record 名相同的构造器块即可。注意:不能调用 this(...),也不能修改 final 字段本身(但可抛异常或提前返回)。
- 校验逻辑写在构造器块内,用
if判断 +throw new IllegalArgumentException(...) - 字段名直接使用(如
name、age),它们是 record 组件,已在构造流程中完成赋值 - 如果校验失败,抛出异常会中断对象创建,不会生成实例
例如:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
Person {
if (name == null || name.trim().isEmpty()) {
throw new IllegalArgumentException("Name cannot be null or blank");
}
if (age 150) {
throw new IllegalArgumentException("Age must be between 0 and 150");
}
}
}
compact constructor 能做什么不能做什么
能做的事:
- 对组件字段做空值、范围、格式等运行时校验
- 将输入标准化(如
name = name.trim()),但注意:record 字段是 final,不能重新赋值;若需标准化,应使用 canonical constructor(传统构造器写法) - 记录日志、触发监听(谨慎,因 record 应保持纯数据性)
不能做的事:
- 给 record 字段重新赋值(编译报错:
cannot assign a value to final variable) - 调用
this(...)或super(...) - 声明参数(compact 形式不允许参数列表)
和 canonical constructor 的区别
如果你需要修改字段值(比如自动 trim 字符串、转小写、装箱等),compact constructor 不够用,得改用 canonical constructor(标准构造器):
record Person(String name, int age) {Person(String name, int age) {
this(name != null ? name.trim() : "", Math.max(0, age));
}
}
此时你显式调用了另一个构造器(隐式或显式),并可在其中做转换;但要注意避免无限递归,且必须最终调用 record 的规范构造路径。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










