SQL中的统计查询 – NHibernate LINQ可以实现吗?

前端之家收集整理的这篇文章主要介绍了SQL中的统计查询 – NHibernate LINQ可以实现吗?前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我有一个应用程序,它使用一些数据仓库原则,如维度建模,在一个相当简单的数据库上进行报告.

名为Call的示例(简化)实体如下所示:

public virtual long Id { get; set; }
    public virtual string OriginatorNumber { get; set; }
    public virtual string DestinationNumber { get; set; }
    public virtual DateDimension DateDimension { get; set; }

实际模型的一些属性已被删除,因为它们无关紧要.简化的DateDimension如下所示:

public virtual long Id { get; set; }
    public virtual DateTime Date { get; set; }
    public virtual int DayOfMonth { get; set; }
    public virtual int Weekday { get; set; }

还有很多这样的专栏 – 它们通过应用程序设置预先填充了当前十年.因此,整个十年中的每个日期在此表中都有一行,每个调用都有一个指向它发生日期的链接.这全部映射在Fluent NHibernate并且工作正常.

如果我想做一些报告,我可以使用3.0中改进的NHibernate LINQ提供程序轻松完成.我们希望使用LINQ来提高我们的可维护性,但如果我们真的必须,我们将考虑HQL,ICriteria甚至纯sql.

所以说我想建立一个报告,显示来自某个数字的呼叫数量除以它们发生的星期几.我可以这样轻松地做到这一点:

var query = Calls
            .Where(c => c.OriginatorNumber == "402")
            .GroupBy(c => c.DateDimension.Weekday)
            .Select(g => new { Day = g.Key,Calls = g.Count() } );

在此示例中,“Calls”基本上是通过存储库接口从NHibernates LINQ提供程序(Query)返回的IQueryable.上面的查询给出了正确的结果,NHibernate Profiler向我展示了sql非常优秀,一切都很好.

但是,如果我想做一些更高级的事情,我会陷入困境.假设我想要每个工作日的平均呼叫次数.离上面不太远吧?我只需要弄清楚每个工作日在结果集中的唯一日期数,除以它的总呼叫次数,我们都设置好了 – 对吗?嗯,不,这是我开始遇到NHibernate LINQ提供程序的限制的地方.使用LINQ to对象,我可以构造一个查询来做到这一点 – 就像一些东西

.Select(g => g.Count() / g.GroupBy(c => c.DateDimension.Date).Count());

但是,在NHibernate中使用它时,这不会转换为正确的查询.相反,它将上面的.Count()调用转换为相同的调用记录数(*),因此结果始终为1.

我当然可以只查询每个调用,工作日和日期作为新的匿名对象,然后在应用程序方面进行数学计算,但根据传统观点,那就是错误(tm).我最终可能会绝望地做到这一点,甚至,当桌子增长到一百万个电话时,这意味着痛苦.

下面是一个SQL查询,它给出了我正在寻找的结果.

select ss.Weekday,AVG(cast(ss.Count as decimal))
from
(
select dd.Weekday,dd.Date,COUNT(*) as Count
from Call c
left outer join DateDimension dd
    on c.DateDimension_id = dd.Id
where c.OriginatorNumber = '402'
group by dd.Weekday,dd.Date
) ss
group by ss.Weekday
order by ss.Weekday

是否可以使用NHibernate LINQ提供程序执行此操作?或者,如果那是不可能的,在我必须让应用程序获取中间结果并完成剩下的工作之前,我能有多接近?

解决方法

LINQ提供程序有很多事情你无法做到.使用HQL或CreateCriteria只是NHibernate必须接受的东西.

我没有尝试过,但看起来你应该能够使用HQL或CreateCriteria(使用DetatchedCriteria)做你想做的事情.

如果你绝望,你也可以使用CreatesqlQuery回退到纯sql.

猜你在找的MsSQL相关文章