C# 在NHibernate中克隆实体?

C# 在NHibernate中克隆实体?,c#,nhibernate,C#,Nhibernate,我想将单个对象保存到数据库两次。我有以下代码: using (var ss = NHibHelp.OpenSession()) using (var tt = ss.BeginTransaction()) { var entity = new Entity(); ss.Save(entity); ss.Save(entity); tt.Commit(); } 但这只会将一行添加到数据库中。如何将单个对象插入数据库两次(使用两个不同的ID)?您不应该这样做-N

我想将单个对象保存到数据库两次。我有以下代码:

using (var ss = NHibHelp.OpenSession())
using (var tt = ss.BeginTransaction())
{
    var entity = new Entity();

    ss.Save(entity);
    ss.Save(entity);

    tt.Commit();
}

但这只会将一行添加到数据库中。如何将单个对象插入数据库两次(使用两个不同的ID)?

您不应该这样做-NHibernate在其会话中维护“对象标识”,因此它不会区分..嗯。。同一个物体。我真的建议不要这样做,一个更好的解决方案是寻找一种克隆对象的方法(通过反射或克隆方法),然后保存克隆的对象

如果您想忽略我上面的建议,可以通过从会话中逐出实体,将其id设置回其未保存的值(取决于您的映射,但可能为0),然后再次保存来让它工作

如果您只调用了session.Merge(entity)两次(在第一次调用之后,您可能需要将id重置为未保存的值),那么它也可能会起作用


或者,您可以将无状态会话与session.Merge()一起使用,这样就不必在Save之间逐出实体。

您可以通过两种方式执行此操作:

  • 克隆实体时,应为深度副本

    using (var ss = NHibHelp.OpenSession())
    using (var tt = ss.BeginTransaction())
    {
      var entity = new Entity();
      var clonedEntity = entity.Clone();
      ss.Save(entity);
      ss.Save(clonedEntity);
    
      tt.Commit();
    }
    
  • 如果您的ID已分配,请记住创建一个新ID。深度复制对于复杂的实体有一些问题,如果您有反向集合,则需要重新引用它们

    2.在新会话中打开第二个事务并提交

    var entity = new Entity();
    using (var ss = NHibHelp.OpenSession())
    using (var tt = ss.BeginTransaction())
    {      
         ss.Save(entity);
    
         tt.Commit();
    }
    
    using (var ss = NHibHelp.OpenSession())
    using (var tt = ss.BeginTransaction())
    {      
         ss.Save(entity);
    
         tt.Commit();
    }
    

    你回答你的问题。克隆您的实体并为克隆的实体设置其他id。在此之后,您将能够将它们分开保存。为什么你不能这样做?@RredCat我希望有更简单的东西,因为在我的实际应用程序中,实体是相当复杂的层次结构的一部分。@RredCat不是这样。第一次调用
    Save
    后,会话将跟踪对象,第二次
    Save
    将什么也不做。@HackedByChinese但第二次您将保存具有相同属性的其他对象(而不是ID)@RredCat您编辑了原始注释(或者至少,我可以发誓您编辑了)。您说过OP的当前代码可以工作(在同一个会话中调用Save两次就可以了)。我是在回应你最初的评论。