【发布时间】:2014-03-13 03:39:53
【问题描述】:
我正在使用 NHibernate 构建一个存储库框架。我的部分要求包括限制返回的结果数量或强制分页。为了让 NHibernate 成功解析来自 IQueryable 表达式的查询,它必须在任何 .Skip().Take() 操作之前执行 OrderBy 或 OrderByDescending 操作。
这就是我当前签名的调用方式。
var actualExerciseJournals = repo.GetAll( pageIndex: pageNum++, recordsPerPage: 250, orderByFirst: exerciseJournal => exerciseJournal.JOURNALDATE, orderBySecond: exerciseJournal => exerciseJournal.MEMBERID);
这是接口签名。
IEnumerable<TEntity> GetAll(int pageIndex, int recordsPerPage, Expression<Func<TEntity, object>> orderByFirst, Expression<Func<TEntity, object>> orderBySecond, Expression<Func<TEntity, object>> orderByThird, Expression<Func<TEntity, object>> orderByFourth, params Expression<Func<TEntity, object>>[] include);
(包含参数与问题无关)
是否可以有一个签名接受这样的参数作为参数?
var actualExerciseJournals = repo.GetAll(pageIndex: 0, recordsPerPage: 250, collectionToOrder => collectionToOrder.OrderBy(x => x.JOURNALDATE).ThenBy(y => y.MEMBERID));
然后我将能够在我的存储库中应用此表达式,并且我将不再对 orderbys 的数量或它是否是 orderbydescending 或其他什么有任何限制。
谢谢
【问题讨论】:
-
等等,什么?为什么不事后订购呢?
-
这可能是返回
IQueryable<T>而不是IEnumerable<T>的候选人 -
我必须在我的存储库中实现 .Skip(x).Take(y)。如果之后添加 .OrderBy,则 NHibernate 在对数据库进行分页时会忽略 OrderBy。
-
.OrderBy(x => x.Col1).ThenBy(x => x.Col2).Skip(250).Take(250) ---- 大致转换为 SQL SELECT TOP 250 * FROM (SELECT TOP 500 ROWNUM(), * FROM Table ORDER BY Col1, Col2) WHERE ROWNUM BETWEEN 250 and 500
-
.Skip(x).Take(y).OrderBy(x => x.Col1).ThenBy(x => x.Col2) 大致转换为 ----- SELECT TOP 250 * FROM (SELECT TOP 500 ROWNUM(), * FROM Table1) WHERE ROWNUM BETWEEN 250 and 500 ORDER BY Col1, Col2