【发布时间】:2015-06-16 09:52:26
【问题描述】:
我在 ASP.NET MVC 5 项目中使用 EF 6.1.3。虽然我的开发环境是 SQL Server 2012,但 QA 和 Production 都是在 SQL Server 2008 R2 上。
我有一份报告显示医生使用的前 5 个程序代码,所以我有一个简单的实体,包含 id、name、code1、code2、...code5。
构建 LINQ 查询有相当多的逻辑,基本上我得到一个医生列表和一个代码列表并加入它们。这是连接它们并选择前 5 个代码的代码:
var report =
from pr in providerRiskLevels
join nc in newCodes on pr.Provider.ProviderId equals nc.ProviderId
where pr.RiskCategoryId == RIskScoreIds.VisibleRisk
&& (filterRiskLevelNums.Contains(pr.RiskLevelNum))
&& (filterSpecialtyId == 0 || pr.Provider.Specialty.SpecialtyId == filterSpecialtyId)
select new ReportNewCodesEntity
{
ProviderId = pr.Provider.ProviderId,
ProviderName = pr.Provider.Name,
ProviderCode = pr.Provider.ProviderCode,
SpecialtyName = pr.Provider.Specialty.Name,
SpecialtyCode = pr.Provider.Specialty.SpecialtyCode,
RiskScore = pr.RiskScore,
RiskLevelName = pr.RiskLevelName,
RiskLevelNum = pr.RiskLevelNum,
NewCode1 = nc.Codes.OrderByDescending(c => c.Volume).FirstOrDefault().ProcedureCode,
NewCode2 = nc.Codes.OrderByDescending(c => c.Volume).Skip(1).FirstOrDefault().ProcedureCode,
NewCode3 = nc.Codes.OrderByDescending(c => c.Volume).Skip(2).FirstOrDefault().ProcedureCode,
NewCode4 = nc.Codes.OrderByDescending(c => c.Volume).Skip(3).FirstOrDefault().ProcedureCode,
NewCode5 = nc.Codes.OrderByDescending(c => c.Volume).Skip(4).FirstOrDefault().ProcedureCode
};
return report;
问题是这四个Skip().FirstOrDefault() 生成的SQL 语法在SQL Server 2008 R2 上不可用:
OFFSET x ROWS FETCH NEXT 1 ROWS ONLY
其中 x = 1 到 4
我确信我可以将其移至存储过程(T-SQL 比 LINQ 好得多),但由于我一直在尝试掌握 LINQ,所以我想知道是否有:
- 一个指令告诉 LINQ 目标数据库的版本,以便生成兼容的代码
- 另一种提取前 5 个代码的方法。
我已经在 newCodes 中正确排序了代码(见下文),但没有 SKIP(需要它自己的排序子句)就无法选择它们。
var newCodes =
from cc in codeCounts
group cc by
new {cc.ProviderId}
into g
select new ProviderNewCodesEntity
{
ProviderId = g.Key.ProviderId,
Codes = g.OrderByDescending (x => x.Volume).Take(5).ToList()
};
最好, 斯科特
【问题讨论】:
-
问题当然是你的开发环境有一个更新版本的sql server,它支持
offset...fetch子句。尝试在你的开发环境中使用 sql server 2008 r2,看看你会得到什么生成的 sql。 (我怀疑前 1 名不在前 4 名,或者类似的东西) -
@Zohar,谢谢,当然是这样。我们知道风险(这就是为什么我们将 QA 保留在与 Prod 相同的版本上)。获得 2008 实例的工作量相当大,所以我尝试了另一种方法,我添加了它作为其他人的答案
标签: linq sql-server-2008-r2 entity-framework-6.1