私はそのような2つのエンティティを持っています(関連するものだけに蒸留されています):
public class Person {
public virtual Address Address
}
public class Address {
}
Person
は と多対 1 の関係にありAddress
、オブジェクト用語では、 a は をPerson
参照してAddress
おり、このリンクは単方向です (Address
には への参照はありませんPerson
)。
さて、このコードを使用すると:
// save a new person with a new address
var person = new Person();
person.Address = new Address();
person.Save();
// change the person's address and save it again
person.Address = new Address();
person.Save();
最初の部分は、想定されていることを実行し、データベースに newPerson
とnew を作成Address
します。
ただし、2 番目の部分は既存の を更新しPerson
て新しい を作成しますAddress
が、孤立した最初のアドレスは削除しません。新しいエンティティへの参照を変更していることを NHibernate に認識させ、孤立したエンティティを自動的に「ガベージ コレクション」するにはどうすればよいですか? または、これを手動で行う必要がありますか?
考えられる解決策
これが実際に起こっていることの決定的な証拠はありませんが、この問題の理由は、オブジェクト リレーショナル インピーダンスの不一致によるものだと思います。プログラミングでは、オブジェクトが他のオブジェクトへの参照を保持していることを知っています。これらの参照が失われると、ガベージ コレクションが行われ、それらを指す参照がなくなった「孤立した」オブジェクトが削除されます。私が提供した例でPerson
は、 への参照がありAddress
、 への参照Address
が失われると、他Persons
にも参照がないと仮定して、ガベージ コレクションが行われます。
データベース側では、ガベージ コレクションの概念はありません。データベースには、1 対多または多対多の関係、つまり、子のコレクションを持つ親のみが存在します。と に戻るPerson
と、これは からまでAddress
の 1 対多の関係であることがわかります(各人は 1 つの住所しか持つことができませんが、住所は、共通の住所を共有する人々の世帯など、多くの人に属することができます)。データベースは、親とを子のコレクションと見なします。したがって、 a を削除しても、も削除されるべきではないことは理にかなっています (別の言い方をすれば、本のコレクションを含む本棚がある場合、本を削除しても本棚は削除されません)。Address
Person
Address
Person
Person
Address
では、これを修正するにはどうすればよいでしょうか。子コレクションが空の親を削除する必要があります。この場合、Address
の空のコレクションを持つ をPersons
削除する必要があります。これはビジネス ルールです。 が単独で存在できないとは何も述べていAddress
ませんが、私が開発しているアプリケーションでは、 がAddress
人に関連付けられていなければ意味がないため、削除する必要があります。ただし、他の誰かがやって来てそれを参照するまで、アドレスが孤立した状態のままになる可能性は十分Person
にあります。