根据标准拆分一个表并进行比较

时间:2012-01-12 16:13:55

标签: sql oracle

我不太确定这个特定查询的最佳方式,所以我希望标题是足够的,但是,我将尝试描述我需要能够理解该怎么做的内容。只是为了澄清,这是针对oracle sql。

我们有一张名为评估的表格。此表中有不同类型的评估,但是,某些评估应按逻辑顺序并在设定的时间范围内跟随其他评估。当客户有多个相同类型的评估时,问题就出现了,因为我们必须在excel中使用效率相当低的数组公式来确定哪个“完整”评估与“初始”评估相对应。

我有一个先前的查询已在此站点上解析(Returning relevant date from multiple tables including additional table info),我认为该查询包含了许多所需的逻辑(特别是在识别在指定时间范围内发生的相应事件时)。然而,虽然该查询从3个单独的表(评估,事件,责任)中提取数据,但我现在需要创建一个生成类似结果的查询,但是从1个主表和第2个表中提取以返回工作人员信息。我认为最合乎逻辑的方法是创建一个查询,用一种评估类型查看评估表,然后再次连接到评估表(可能是临时表?),其评估类型将遵循初始评估类型。

例如:

表1(评估):

Client    ID    Assessment Type   Start       End
P1        1     Initial           01/01/2012  05/01/2012

表2(评估温度?):

Client ID    Assessment Type   Start       End
P1     2     Full              12/01/2012 

表3:

ID     Worker     Team
1      Bob        Team1
2      Lyn        Team2

结果:

Client  ID    Initial Start    Initial End    Initial Worker   Full Start   Full End   
P1      1     01/01/2012       05/01/2012     Bob              12/01/2012

所以表1和表2从同一张表中抽取,除了它带回了不同的评估。理想情况下,需要检查以确保“初始”评估在“初始”评估结束后的X天内开始(类似于前面提到的上一个查询中的“可能”检查)。如果可以实现这一目标,可能值得一提的是,我也有兴趣将其扩展到多种评估类型,大致在周期中客户可能会有4到5种不同类型的评估。任何指针都会受到赞赏,我已经从这个社区得到了很多帮助,这非常有价值。

编辑:

根据MB建议编辑包含解决方案。

Select
*
From(
Select
I.ASM_SUBJECT_ID as PNo,
I.ASM_ID As IAID,
I.ASM_QSA_ID as IAType,
I.ASM_START_DATE as IAStart,
I.ASM_END_DATE as IAEnd,
nvl(olm_bo.get_ref_desc(I.ASM_OUTCOME,'ASM_OUTCOME'),'') as IAOutcome,
C.ASM_ID as CAID,
C.ASM_QSA_ID as CAType,
C.ASM_START_DATE as CAStart,
C.ASM_END_DATE as CAEnd,
nvl(olm_bo.get_ref_desc(C.ASM_OUTCOME,'ASM_OUTCOME'),'') as CAOutcome,
ROUND(C.ASM_START_DATE -I.ASM_START_DATE,0) as "Likely",
row_number() over(PARTITION BY  I.ASM_ID                   
ORDER BY 
abs(I.ASM_START_DATE -  C.ASM_START_DATE))as "Row Number"
FROM
O_ASSESSMENTS I
left join O_ASSESSMENTS C
on I.ASM_SUBJECT_ID = C.ASM_SUBJECT_ID
and C.ASM_QSA_ID  IN ('AA523','AA1326') and
ROUND(C.ASM_START_DATE - I.ASM_START_DATE,0) >= -2
AND
ROUND(C.ASM_START_DATE -  I.ASM_START_DATE,0) <= 25
and C.ASM_OUTCOME <>'ABANDON'
Where I.ASM_QSA_ID  IN ('AA501','AA1323')
AND I.ASM_OUTCOME <> 'ABANDON'
AND
I.ASM_END_DATE >= '01-04-2011') WHERE "Row Number" = 1 

2 个答案:

答案 0 :(得分:3)

您可以在SQL中的给定查询中多次访问同一个表,只需使用表别名即可。所以这样做的一种方法是:

select i.client,
       i.id     initial_id,
       i.start  initial_start,
       i.end    initial_end,
       w.worker initial_worker,
       f.id     full_id,
       f.start  full_start,
       f.end    full_end
from assessments i
join workers w on i.id = w.id
left join assessments f 
       on i.client = f.client and 
          f.assessment_type = 'Full' and
          f.start between i.end and i.end + X 
/* replace X with appropriate number of days */
where i.assessment_type = 'Initial'

注意:诸如end之类的列名(在Oracle SQL中是保留字)通常应该是双引号,但从上一个问题看,它们看起来好像是实际列名的简化版本。 / p>

答案 1 :(得分:1)

从您的帖子中,我假设您在这里使用Oracle(因为我在问题中看到了“Oracle”)。

就“临时”表而言,意见正确。 Oracle View可以为您提供不同的表格外观,这就是您通过不同类型的评估所寻找的内容。

唐·伯莱森(Don Burleson)是Oracle相关内容的良好来源,他在http://www.dba-oracle.com/concepts/views.htm提供了有关Oracle视图的一些提示