2

親テーブルと子テーブルがあります。Child には、1 対多の関係を作成する Parent テーブルへの外部キーが含まれています。以下は、流暢な NHibernate で定義したマッピングの一部です。

public class ParentMap : ClassMap<Parent>
{
    public ParentMap()
    {
        WithTable("Parents");

        Id(x => x.Id, "ParentID")
        .WithUnsavedValue(0)
        .GeneratedBy.Identity();

        Map(x => x.Description, "Description");

        HasMany<Child>(x => x.Childs)
        .LazyLoad()
        .WithKeyColumn("ParentID")
        .IsInverse()
        .AsSet();
    }
}

public class ChildMap : ClassMap<Child>
{
    public ChildMap()
    {
        WithTable("Childs");

        Id(x => x.Id, "ChildID")
        .WithUnsavedValue(0)
        .GeneratedBy.Identity();

        References(x => x.Parent, "ParentID")
            .CanNotBeNull()
            .LazyLoad();
    }
}

ご覧のとおり、リレーションに LazyLoad を設定しました。私のモデル クラスでは、すべてのプロパティが仮想として設定されていることにも注意してください。

次に、簡単なクエリを実行します。

ICriteria crit = Session.CreateCriteria(typeof(Child))
    .Add(Expression.Eq("Id", 18));
IList<Child> list = crit.List<Child>();

そして生成されたSQL:

SELECT this_.ChildID            as ChildID5_1_,
       this_.ParentID           as ParentID5_1_,
       parent2_.ParentID    as ParentID4_0_,
       parent2_.Description as Descript2_4_0_
FROM   Childs this_
       inner join Parents parent2_
         on this_.ParentID = parent2_.ParentID
WHERE  this_.ChildID = 18 /* @p0 */

ご覧のとおり、親テーブルで結合を行い、そのフィールド (id と説明) を選択します。しかし、遅延読み込みを要求したので、なぜそれを行うのですか?

クエリを次のように変更すると:

ICriteria crit2 = Session.CreateCriteria(typeof(Child))
    .SetFetchMode("Parent", FetchMode.Lazy)
    .Add(Expression.Eq("Id", 18));

2 つの SQL クエリが生成されます。

SELECT this_.ChildID  as ChildID5_0_,
       this_.ParentID as ParentID5_0_
FROM   Childs this_
WHERE  this_.ChildID = 18 /* @p0 */

これは私にとって良いことです: 結合なし、親テーブルは照会されません。しかし、私はこの2番目のものも取得します:

SELECT parent0_.ParentID    as ParentID4_0_,
       parent0_.Description as Descript2_4_0_
FROM   Parents parent0_
WHERE  parent0_.ParentID = 45 /* @p0 */

親テーブルを再度クエリします。

これらの 2 つのクエリは、ライン中に生成されます。

IList<Child> list = crit.List<Child>();

私はここで何が起こっているのか全く知りません。誰か助けてくれませんか?

4

1 に答える 1

6

Fluent NHibernate のバージョンによって異なります。ある時点まで、すべてのエンティティが遅延ロードされないことがデフォルトでした。これは、lazy="false"エンティティで明示的に設定することと同じです。これはもはや当てはまりませんが、その時点より前に何かを実行している場合は、この動作が見られます。

多対 1/参照の遅延読み込み設定は、ターゲットからのエンティティ レベルの遅延読み込みによってオーバーライドされるため、この古いバージョンの FNH で実行している場合、エンティティ設定はReferences(...).LazyLoad()呼び出しを意味のないものにします。

FNH の最新バージョンを使用していることを確認する必要があります。これにより問題が修正されるはずです。ただし、そうでない場合は、Parentエンティティで遅延読み込みを明示的に設定する必要があります。LazyLoadのメソッドでそれを行うことができますClassMap<T>

于 2009-01-26T12:19:57.320 に答える