類似の質問が 2 件見つかりました:
によるとこのページ:
複数のコレクション プロパティを同時に積極的にフェッチしないように注意してください。次のステートメントは問題なく動作しますが、
var employees = session.Query<Employee>() .Fetch(e => e.Subordinates) .Fetch(e => e.Orders).ToList();
これはデータベースに対して直積クエリを実行するため、返される行の合計数は、下位の合計数と順序の合計数を掛け合わせた数になります。
次のようなモデルがあるとします。
public class Person
{
public virtual int Id { get; private set; }
public virtual ICollection<Book> Books { get; set; }
public virtual ICollection<Article> Articles { get; set; }
public virtual ICollection<Address> Addresses { get; set; }
}
QueryOver/Linq を使用して (デカルト積を返さずに) すべての人物とその書籍、記事、住所を積極的に読み込む最も簡単な方法は何ですか?
ありがとう
アップデート:
見るクレモールの答え以下、フロリアン・リムの答えでこのスレッド次のコードは、データベースへの往復が 1 回のみで、正常に動作します。
var persons = session.QueryOver<Person>()
.Future<Person>();
var persons2 = session.QueryOver<Person>()
.Fetch(x => x.Books).Eager
.Future<Person>();
var persons3 = session.QueryOver<Person>()
.Fetch(x => x.Articles).Eager
.Future<Person>();
var persons4 = session.QueryOver<Person>()
.Fetch(x => x.Addresses).Eager
.Future<Person>();
ベストアンサー1
特に nhibernate の新しいバージョン (>= 4.0) を使用している場合は、可能な限り linq プロバイダーを使用することをお勧めします。コレクションを ISets (.net フレームワーク >= 4 が必要) としてマップしておけば、これを変換して、積分を回避して、積分を迅速にロードできます。これはあまり宣伝されていないようですが、適用可能な場合は他の方法よりもこの方法を好みます。
public class Person
{
public virtual int Id { get; private set; }
public virtual ISet<Book> Books { get; set; }
public virtual ISet<Article> Articles { get; set; }
public virtual ISet<Address> Addresses { get; set; }
}
public Person()
{
this.Books = new HashSet<Book>();
this.Articles = new HashSet<Article>();
this.Addresses = new HashSet<Address>();
}
上記のようにコレクションを定義している場合は、次の操作を実行しても、直積の問題を回避できます。
var persons = session.Query<Person>()
.FetchMany(x => x.Books)
.FetchMany(x => x.Articles)
.FetchMany(x => x.Addresses)
.ToList();