如何在NHibernate中进行此投影?

时间:2011-08-06 12:05:03

标签: database nhibernate queryover

我的数据库中有这些实体

enter image description here

对于给定的Job,我希望基本上以下列形式获得结果

<Translation>,<ExternalUnit.Text>,<ExternalTranslation.Text>

其中连接条件是Translation.Unit.Text == ExternalUnit.Text

这是我到目前为止所做的,工作正常:

var props = session.QueryOver<Translation>(() => translation)
            .Select(c => translation.Id, c => externalUnit.Text, c => externalTranslation.Text)
            .JoinAlias(() => translation.TranslationUnit, () => unit)                
            .JoinAlias(() => unit.Job, () => job)
            .Where(() => unit.Job == job)
            .JoinAlias(() => job.ExternalUnits, () => externalUnit)
            .JoinAlias(() => externalUnit.ExternalTranslations, () => externalTranslation)
            .Where(() => externalUnit.Text == unit.Text)
            .List<object[]>();

var translations = session.QueryOver<Translation>(() => translation)                
            .JoinAlias(() => translation.TranslationUnit, () => unit)                
            .JoinAlias(() => unit.Job, () => job)
            .Where(() => unit.Job == job)
            .JoinAlias(() => job.ExternalUnits, () => externalUnit)
            .JoinAlias(() => externalUnit.ExternalTranslations, () => externalTranslation)
            .Where(() => externalUnit.Text == unit.Text)
            .List<Translation>()
            .ToList();

然后我循环浏览translations,引用props。但是,我不喜欢这种方法,因为我不必要地对数据库执行两个(几乎相同的)查询而不是一个。

但我无法完成所需的投影工作。我在考虑这样的事情:

var data = session.QueryOver<Translation>(() => translationAlias)                
            .JoinAlias(() => translation.TranslationUnit, () => unit)                
            .JoinAlias(() => unit.Job, () => job)
            .Where(() => unit.Job == job)
            .JoinAlias(() => job.ExternalUnits, () => externalUnit)
            .JoinAlias(() => externalUnit.ExternalTranslations, () => externalTranslation)
            .Where(() => externalUnit.Text == unit.Text)
            .Select(() => translation, () => externalUnit.Text, () => externalTranslation.Text)
            .List()

但是,显然,NHibernate不喜欢Select(() => translation...)位(它不允许我投影整个实体)。

理想情况下,我想选择匿名类型,例如

var data = session.QueryOver<Translation>()
             ...
             .Select(() => new { A = translation, B = externalTranslation })

但我觉得NHibernate到目前为止还不存在......

非常感谢您的任何建议。

1 个答案:

答案 0 :(得分:0)

我知道了! NHibernate的LINQ提供程序救了我。它的优点在于它可以选择匿名类型,这使得连接变得更加容易。为了防止有人好奇,这是针对我的具体情况:

var q = 
(from c in
  (from b in            
    (from translation in session.Query<Translation>()
     join unit in units on translation.Unit equals unit
     where unit.Job == job
     select new { Translation = translation, Original = unit.Text })         
   join extUnit in externalUnits on job equals extUnit.Job
   where extUnit.Text == b.Original
   select new { Translation = b.Translation, ExternalUnit = extUnit })
 join extTranslation in extTranslations on c.ExternalUnit equals extTranslation.Unit
 select new { Translation = c.Translation, Suggestion = extTranslation })
 .ToList();

它生成的SQL非常合理,所以我很高兴:)