web-dev-qa-db-ja.com

NHibernateの逆属性

逆属性を使用するにはどうすればよいですか?誤解しない限り、1対多の関係では、逆属性をtrueに設定する必要があります。多対多の関係では、エンティティクラスの逆属性の1つをtrueに設定し、別の属性をfalseに設定する必要があります。

誰でもこれにいくつかの光を当てることができますか?

87
Graviton

逆属性をtrueに設定しないでください...

インバース属性を使用して、関連付けの「所有者」を指定します。 (アソシエーションには1人の所有者しか設定できないため、一方の端を逆に設定し、もう一方の端を「非逆」に設定する必要があります)。 (所有者:inverse=false;非所有者:inverse=true

1対多の関連付けでは、コレクションをインバースエンドとしてマークしない場合、NHibernateは追加のUPDATEを実行します。実際、この場合、NHibernateはまずコレクションに含まれるエンティティを挿入し、必要に応じてコレクションを所有するエンティティを挿入し、その後、「コレクションエンティティ」を更新して、外部キーが設定され、関連付けが行われるようにします作られています。 (これは、DBの外部キーがNULL可能であることも意味することに注意してください)。

コレクションの終わりを「逆」としてマークすると、NHibernateは最初にコレクションを「所有」するエンティティを永続化し、その後コレクションにあるエンティティを永続化し、追加のUPDATEステートメントを回避します。

そのため、双方向の関連付けでは、常に1つの逆端があります。

121

上記の答え に加えて、私の理解によれば、コレクション内の外部キー値を手動で永続化する必要があります。これは、追加の更新ステートメントが必要ない場合です。

Parent par = Session.Get<Parent>(8);

Child ch = new Child();
ch.Name = "Emad";

//set the parent foreign key manually
ch.MyParent = par;

par.MyChildren.Add(ch);
Session.Save(par);

逆属性の詳細については、次の投稿を確認してください。

http://www.emadashi.com/index.php/2008/08/nhibernate-inverse-attribute/

10
Emad Alashi

「所有者」がどこに来るかはわかりますが、アソシエーションはパイプであり、どちらの端も見下ろすことができます。

これを見る別の方法は、1対多の関係では、実際には2つの関係が進行しているということです。

関係1:多くの子供への親。

関係2:各子と親

そのため、NHはsqlを実行してこれらのそれぞれをDBに保存しようとします。しかし、外部キーを設定するとリレーションシップ2では、子が格納されると、リレーションシップ1はリレーションシップ2の「逆」であるため、親と子のリレーションシップも自動的に修正されます。

つまり、逆とは、主な関係を設定するとデフォルトで取得されることを意味します。つまり、NHがsqlを実行してリレーションシップ1を修正する必要はなく、子コレクションをInverse NHとしてマークすると、子コレクションが追加されたときにsqlの実行がスキップされます。

NHにそれが逆であると言わなかったら、逆の関係も同様に設定しようとするためにsqlを行うのに労力を浪費すると思います-必要はありませんでした。

2
Mickey Puri