CTE未正确评估所有选择标准

时间:2011-09-08 16:45:44

标签: sql-server-2005 tsql common-table-expression

早上好,

我编写了以下存储过程,用于搜索指定为指定过程的一个或多个费用代码的记录,并将其标记为ProcGrouper = 1,并且需要识别那些没有对比费用的帐户(标记为ContrastGrouper = 0)。

当我运行sproc和审计帐户时,我看到很多都有对比费用。因此,似乎CTE没有正确评估所有标准。我该如何解决这个问题?

with cteGrouper
as
(
SELECT [ENCOUNTER NUMBER],
[DATE OF SERVICE], [FEEDER KEY],
[CHGDTL CPT4 CODE], CASE
WHen [FEEDER KEY] IN ('76803520121','76803520120','76803520112','76803520111',
'76803520110','76803520109','76803520108','76803520034','76803520030','76803520027',
'76803520025','76803520017','76803520015','76803520014','76803510073','76803510072',
'76803510064','76803510012','76803510011','76803510008','76803510003','76803510002',
'76803510068','76803520031','76803520028','76803520107','76803520022','76803520020',
'76803520106','76803510009','76803510070','76803510069','76803510067','76803510065',
'76803510074','76704027052','76606123003','76606123001','76606120012','76606111003',
'76606102043','76606100011','76606102040','76606121006','76606121009','76606123002',
'76606102053','76606102042') then 1 else 0
end as ProcGrouper, 
Case when [Feeder Key] in ('76806360076', '76806360077','76806360089','76806360090',
'76306360509','76306360513','76306360514','75706362105','76806366053','75706366054',
'75706366055','76606360099') then 1 else 0
end as ContrastGrouper
FROM ENCOUNTERCHGDTL
where ([Date of Service] between @StartDate and @EndDate)
),
cteFilterAccounts
as
(
Select [Encounter Number],
[Date of Service], [Feeder Key],
[Chgdtl CPT4 Code], ProcGrouper, ContrastGrouper
from cteGrouper
where ProcGrouper=1
and ContrastGrouper=1
)

Select [Encounter Number],
[Feeder Key],
[Date of Service],
[Chgdtl CPT4 Code]
,[ADMITDATE - CCYYMMDD], [DISCHARGEDATE - CCYYMMDD],
[DISCHARGEDISPOSITION], ProcGrouper, ContrastGrouper
from cteGrouper
join Encounter on [Encounter Number]=[EncounterNumber]
and AdmitSubService <>'SIG' 
and HSP#='1'
and ActualTotalCharge>0
where ProcGrouper=1 
and ContrastGrouper=0
and [Encounter Number] not in
(Select [Encounter Number] from cteFilterAccounts)

Order by [ENCOUNTER NUMBER]
END

1 个答案:

答案 0 :(得分:1)

我认为您应该重新定义cteFilterAccounts CTE。问题是,您当前CTE的代码返回的集合中cteGroup的每个个人行同时包含ProcGrouper=1 ContrastGrouper=1 。基于cteGroup的代码,这是永远不可能的,因为一行可以有[Feeder Key]属于不超过一个的两个组,所以它是 ProcGrouper=1 ContrastGrouper=1,但不是两者。因此,CTE什么都不返回。

但从逻辑上讲,您似乎正在搜索在全局范围内设置了两个属性的行,即期间的。一种可能的解决方案是使用连接,如下所示:

cteFilterAccounts AS (
  SELECT g1.[Encounter Number]
  FROM (
    SELECT DISTINCT [Encounter Number],
    FROM cteGrouper
    WHERE ProcGrouper=1
  ) g1
  INNER JOIN (
    SELECT DISTINCT [Encounter Number],
    FROM cteGrouper
    WHERE ContrastGrouper=1
  ) g2 ON g1.[Encounter Number] = g2.[Encounter Number]
)

此查询将所有[Encounter Number]值与来自该时段内找到的一个组的[Feeder Key]连接在一起,其中[Feeder Key]属于另一个组。匹配值为您提供结果集。

或者你可以使用INTERSECT:

cteFilterAccounts AS (
  SELECT [Encounter Number],
  FROM cteGrouper
  WHERE ProcGrouper=1
  INTERSECT
  SELECT [Encounter Number],
  FROM cteGrouper
  WHERE ContrastGrouper=1
)

基本上,它使用与join相同的逻辑。

你也可以尝试一种完全不同的方法,分组,如下:

cteFilterAccounts AS (
  SELECT [Encounter Number]
  FROM cteGrouper
  GROUP BY [Encounter Number]
  HAVING MAX(ProcGrouper) = 1
     AND MAX(ContrastGrouper) = 1
)

在这里,您要选择的Grouper属性“最大(聚合)值等于1的不同帐户。