Hibernate中persist()和merge()之间有什么区别? [英] What is the difference between persist() and merge() in Hibernate?

查看:142
本文介绍了Hibernate中persist()和merge()之间有什么区别?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Hibernate中persist()和merge()之间有什么区别?

persist() can创建一个UPDATE& INSERT查询,例如:

  SessionFactory sef = cfg.buildSessionFactory(); 
Session session = sef.openSession();
A a = new A();
session.persist(a);
a.setName(Mario);
session.flush();

在这种情况下,查询将会像这样生成:

  Hibernate:插入A(NAME,ID)值(?,?)
Hibernate:update一组NAME =?其中ID =?

so persist() method can 生成插入和更新。



现在使用 merge()

  SessionFactory sef = cfg.buildSessionFactory(); 
Session session = sef.openSession();
歌手歌手=新歌手();
singer.setName(Luciano Pavarotti);
session.merge(歌手);
session.flush();

这就是我在数据库中看到的结果:

  SINGER_ID SINGER_NAME 
1 Ricky Martin
2 Madonna
3 Elvis Presley
4 Luciano Pavarotti

现在使用 merge()

更新记录

  SessionFactory sef = cfg.buildSessionFactory(); 
Session session = sef.openSession();
歌手歌手=新歌手();
singer.setId(2);
singer.setName(Luciano Pavarotti);
session.merge(歌手);
session.flush();

这就是我在数据库中看到的结果:

  SINGER_ID SINGER_NAME 
1 Ricky Martin
2 Luciano Pavarotti
3 Elvis Presley


解决方案

JPA规范包含这些操作的语义的非常精确的描述,比在javadoc中更好:


应用于实体X的 persist
操作的语义是
,如下所示:


  • 如果X是一个新的实体,那么
    就会被管理。实体X将在
    事务提交或之前输入到数据库中
    ,或者作为
    刷新操作的结果。


  • 如果X是一个
    先前存在的被管实体,那么被持久化操作忽略

    但是,如果从X到这些
    其他实体的关系用
    <$ c $注释,则坚持操作是
    级联到由X引用的实体,
    c> cascade = PERSIST 或 cascade = ALL
    注释元素值或指定的
    与等价的XML描述符
    元素。

  • 如果X是已删除的实体,则
    将被管理。


  • 如果X是一个
    分离对象,当调用persist操作时,
    EntityExistsException 可能被抛出

    EntityExistsException
    另一个 PersistenceException 可能是
    在刷新或提交时抛出。

  • 对于
    所有实体Y,如果与Y的
    关系已被注释,则由X中的
    关系引用
    与级联元素值
    cascade = PERSIST cascade = ALL
    坚持操作离子适用于Y.








< blockquote>

适用于实体X的 merge 操作
的语义如下:


  • 如果X是分离的实体,则X的状态
    被复制到同一
    标识的预先存在的
    托管实体实例X'中,或者创建X
    的新托管副本X'。如果X是新实体
    实例,则新的托管实体
    实例X'被创建,并且X的状态
    被复制到新的托管
    实体实例X'中。

  • 如果X是已删除
    的实体实例,则
    IllegalArgumentException 将为合并操作(或
    事务)抛出的
    如果X
    是一个托管实体,它将被合并操作的
    忽略,但是,
    合并操作被级联到
    实体由关系引用
    如果这些关系具有
    已注释了级联
    元素值 cascade = MERGE
    cascade = ALL 注解。
  • 从X具有级联元素
    cascade = MERGE cascade = ALL 的关系
    , Y
    被递归合并为Y'。对于由X引用的所有
    这样的Y,将X'设置为
    引用Y'。 (注意,如果X是
    ,那么X与
    X'是同一个对象。)


  • 如果X是实体合并到X',
    并引用另一个实体Y,
    ,其中 cascade = MERGE cascade = ALL 是未指定的
    ,则从X'导航
    相同的关联会产生一个
    对托管对象Y'的引用,其中
    具有与Y相同的持久性标识。

    What is the difference between persist() and merge() in Hibernate?

    persist() can create a UPDATE & INSERT query, eg:

    SessionFactory sef = cfg.buildSessionFactory();
    Session session = sef.openSession();
    A a=new A();
    session.persist(a);
    a.setName("Mario");
    session.flush();
    

    in this case query will be generated like this:

    Hibernate: insert into A (NAME, ID) values (?, ?)
    Hibernate: update A set NAME=? where ID=?
    

    so persist() method can generate an Insert and an Update.

    Now with merge():

    SessionFactory sef = cfg.buildSessionFactory();
    Session session = sef.openSession();
    Singer singer = new Singer();
    singer.setName("Luciano Pavarotti");
    session.merge(singer);
    session.flush();
    

    This is what I see in the database:

    SINGER_ID   SINGER_NAME
    1           Ricky Martin
    2           Madonna
    3           Elvis Presley
    4           Luciano Pavarotti
    

    Now update a record using merge()

    SessionFactory sef = cfg.buildSessionFactory();
    Session session = sef.openSession();
    Singer singer = new Singer();
    singer.setId(2);
    singer.setName("Luciano Pavarotti");
    session.merge(singer);
    session.flush();
    

    This is what I see in the database:

    SINGER_ID   SINGER_NAME
    1           Ricky Martin
    2           Luciano Pavarotti
    3           Elvis Presley
    

    解决方案

    JPA specification contains a very precise description of semantics of these operations, better than in javadoc:

    The semantics of the persist operation, applied to an entity X are as follows:

    • If X is a new entity, it becomes managed. The entity X will be entered into the database at or before transaction commit or as a result of the flush operation.

    • If X is a preexisting managed entity, it is ignored by the persist operation. However, the persist operation is cascaded to entities referenced by X, if the relationships from X to these other entities are annotated with the cascade=PERSIST or cascade=ALL annotation element value or specified with the equivalent XML descriptor element.

    • If X is a removed entity, it becomes managed.

    • If X is a detached object, the EntityExistsException may be thrown when the persist operation is invoked, or the EntityExistsException or another PersistenceException may be thrown at flush or commit time.

    • For all entities Y referenced by a relationship from X, if the relationship to Y has been annotated with the cascade element value cascade=PERSIST or cascade=ALL, the persist operation is applied to Y.


    The semantics of the merge operation applied to an entity X are as follows:

    • If X is a detached entity, the state of X is copied onto a pre-existing managed entity instance X' of the same identity or a new managed copy X' of X is created.

    • If X is a new entity instance, a new managed entity instance X' is created and the state of X is copied into the new managed entity instance X'.

    • If X is a removed entity instance, an IllegalArgumentException will be thrown by the merge operation (or the transaction commit will fail).

    • If X is a managed entity, it is ignored by the merge operation, however, the merge operation is cascaded to entities referenced by relationships from X if these relationships have been annotated with the cascade element value cascade=MERGE or cascade=ALL annotation.

    • For all entities Y referenced by relationships from X having the cascade element value cascade=MERGE or cascade=ALL, Y is merged recursively as Y'. For all such Y referenced by X, X' is set to reference Y'. (Note that if X is managed then X is the same object as X'.)

    • If X is an entity merged to X', with a reference to another entity Y, where cascade=MERGE or cascade=ALL is not specified, then navigation of the same association from X' yields a reference to a managed object Y' with the same persistent identity as Y.

    这篇关于Hibernate中persist()和merge()之间有什么区别?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆