hibernate对象有三种状态:瞬时态(无主键、未关联session、数据库无记录)、持久态(有主键、被session缓存管理、数据库有对应记录,支持自动同步)、游离态(有主键、数据库有记录但脱离session管理,需update/saveorupdate重新关联)。

Hibernate 通过 Session 管理 Java 对象与数据库记录之间的映射关系,对象状态本质上反映的是“是否被当前 Session 跟踪”以及“是否在数据库中有对应记录”。核心就三点:有没有主键(OID)、有没有被 Session 缓存、数据库里有没有那条数据。
瞬时态(Transient):刚 new 出来,谁也不认识
对象刚用 new 创建,没设主键(id 为 null 或默认值),没和任何 Session 关联,数据库里也查不到它。它只是 JVM 里一块普通内存。
- 典型场景:
User user = new User(); user.setName("张三"); - 此时调用
session.get(User.class, 1L)或session.load(...)不会返回它,因为它不在 Session 缓存中,也不对应数据库记录 - 它不会触发任何 SQL,也不会被 Hibernate 自动同步
持久态(Persistent):Session 正在盯着,数据库里有它
对象有合法主键(OID),且正被当前 Session 缓存管理——它和数据库某条记录严格对应。Session 在 flush 或 commit 时,会自动检测它的变化并执行 UPDATE(脏检查)。
Java项目代码review工具。分析Git变更+完整调用链路上下文,推断业务需求,进行多维度评分和分类汇总,生成完整PRD文档。包含细粒度Java代码审查清单(Null安全、异常处理、Streams、并发、equals/hashCode、资源管理、API设计、性能、MyBatis/ORM、事务边界、SQL/DD...
- 进入方式:调用
session.save()(瞬时 → 持久)、session.get()/session.load()(从 DB 查出 → 持久)、session.merge()(游离 → 持久副本) - 关键特征:修改属性后无需手动 update;事务提交时自动同步;关闭 Session 后立刻变游离
- 注意:
save()在主键策略为identity时立即 INSERT 获取 ID;若为increment,则先查最大 ID 再 INSERT
游离态(Detached):曾经被管过,现在单飞了
对象有主键、数据库里有对应记录,但已脱离当前 Session 管理——比如 Session.close()、session.clear()、session.evict(obj) 后,或者跨事务传递(如 Web 层传参)。
- 典型场景:用户在页面修改了一个从数据库查出的对象,然后提交表单,在新事务中处理 —— 提交时这个对象就是游离态
- 不能直接修改就保存:对游离对象改属性,Session 不知道,也不会同步到 DB
- 重新关联方式:
session.update(obj)(强制更新,要求主键存在)、session.saveOrUpdate(obj)(自动判断:有 ID 就 update,无 ID 就 save)、session.lock(obj, LockMode.NONE)(仅重关联,不更新) - 也可用
session.merge(obj):它不修改原对象,而是返回一个持久态副本,原对象仍游离
补充:delete 和删除态(DELETED)
调用 session.delete(obj) 后,该对象进入删除态(Hibernate 内部状态码 DELETED=3),表示已计划删除。它仍可访问属性,但不能再被 save/update;事务提交后,数据库记录被删,Session 缓存中移除。
- 注意:
delete()对瞬时对象抛异常;对游离对象会先 reattach 再删(需确保主键有效) - 删除态不是常用编程接口状态,开发中一般只关注 transient/persistent/detached 三种
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










