persist、merge、save总结

来源:互联网 发布:2017达内网络视频课程 编辑:程序博客网 时间:2024/05/20 11:20
  • persist() makes a transient instance persistent. However, it does not guarantee that the identifier value will be assigned to the persistent instance immediately, the assignment might happen at flush time. persist() also guarantees that it will not execute an INSERT statement if it is called outside of transaction boundaries. This is useful in long-running conversations with an extended Session/persistence context.

  • save() does guarantee to return an identifier. If an INSERT has to be executed to get the identifier ( e.g. "identity" generator, not "sequence"), this INSERT happens immediately, no matter if you are inside or outside of a transaction. This is problematic in a long-running conversation with an extended Session/persistence context.

    persist():

    将瞬态实例变成持久态。然而,不能保证立即返回实例的标识符,也可能在flush的时候将标识符赋值给实例。

    persist方法也保证在事务边界外不执行INSERT。在长运行带扩展的Session/persistence上下文的会话。
    save():

    保证返回一个标识符。如果需要通过INSERT获取了标识符(例如:“identity”而非“sequence”生成器),INSERT立即执行。

    不论是否在事务内外。这会在长运行带扩展的Session/persistence上下文的会话中出现问题。


    再来看merge()方法的注释:


    /**
    * Copy the state of the given object onto the persistent object with the same
    * identifier. If there is no persistent instance currently associated with
    * the session, it will be loaded. Return the persistent instance. If the
    * given instance is unsaved, save a copy of and return it as a newly persistent
    * instance. The given instance does not become associated with the session.
    * This operation cascades to associated instances if the association is mapped
    * with {@code cascade="merge"}
    * <p/>
    * The semantics of this method are defined by JSR-220.
    *
    * @param object a detached instance with state to be copied
    *
    * @return an updated persistent instance
    */

    将对象的状态拷贝到与对象标识符相同的持久化对象中去,如果没有找到对应与session关联的对象。则从数据库中查一下,如果数据库中

    有记录,merge方法返回持久化实例。如果被给的实例是未保存(对应数据库里没有记录)的,保存实例的副本然后作为一个新的持久化实例返回。

    该实例并没有与session关联。


    测试persist和merge:

    persist:

    1)persist一个瞬态实例,该实例不在sessio中,数据库里有对应记录

    result: com.mysql.jdbc.exceptions.MySQLIntegrityConstraintViolationException: Duplicate entry '1' for key 'PRIMARY'

    2) persist 一个瞬态实例,该实例在session中,数据库有对应的记录

    result: org.hibernate.NonUniqueObjectException: A different object with the same identifier value was already associated with the session 

    3)persist一个持久化实例,实例在session中,数据库有对应记录

    result:如果改持久化实例没变化则不发sql,有变化则发sql,update。

    emerge:

    1)emerge一个瞬态实例,改实例不在session中

    result:发一条sql,比较实例和session中实例的差别,有变化则做更新。反之,不做任何操作。

    其他测试,大家可以测试一下。


0 0
原创粉丝点击