2012-11-06 75 views
1

我有以下查询:一个日期检查整个查询

select 
    fp.id, 
    fr.id, 
    sum(case 
     when to_date(fp.offered_date) BETWEEN TO_DATE(:ad_startdate, 'YYYY-MM-DD') 
      AND TO_DATE(:ad_enddate, 'YYYY-MM-DD') and fp.result <> 'E' 
      then 1 
     else 0 
     end) total, 
    sum(case when fp.result = 'G' 
     and to_date(fp.offered_date) >= :ad_startdate 
     and to_date(fp.offered_date) <= :ad_enddate then 1 else 0 end) colorgreen, 
    sum(case when fp.resultat = 'R' 
     and to_date(fp.offered_date) >= :ad_startdate 
     and to_date(fp.offered_date) <= :ad_enddate then 1 else 0 end) colorred 
FROM 
    fruit_properties fp, fruit fr 
WHERE 
    fp.id = fr.id 
GROUP BY 
    fp.id, fr.id 

我检查日期1次次金额列,并有此可一次不知何故的感觉?现在,如果我只在总列中检查一次,那么colorgreen + colorred可能会比总数大,因为无论它们具有哪个日期,它都会计数。

我的查询可以以某种方式增强吗?

回答

2

你可以这样简化。但请检查你的SQL。你在混合TO_DATE和CHAR数据类型。这只会在灾难中结束。

如您有:

when to_date(fp.offered_date) BETWEEN TO_DATE(:ad_startdate, 'YYYY-MM-DD') 
      AND TO_DATE(:ad_enddate, 'YYYY-MM-DD') 

VS

sum(case when fp.result = 'G' 
    and to_date(fp.offered_date) >= :ad_startdate 

在一种情况下,你都TO_DATE'ing ad_startdate而不是另一个(所以它是一个日期已经或没有?)。你也是TO_DATEing列,但关键没有格式掩码。该列是否真的是VARCHAR数据类型?如果是这样的话,你真的不应该将日期存储为日期而不是日期。

反正假设列是一个DATE数据类型和结合是DATE类型..

select fruit_prop_Id,fruit_id, 
     sum(case when result != 'E' then within_offer else 0 end) total, 
     sum(case when result = 'R' then within_offer else 0 end) colorred, 
     sum(case when result = 'G' then within_offer else 0 end) colorgreen 
from (select fp.id fruit_id, 
       fr.id fruit_prop_Id, 
       fp.result, 
       case 
        when fp.offered_date >= :ad_startdate 
        and fp.offered_date <= :ad_enddate then 1 else 0 end within_offer 
     from fruit_properties fp, fruit fr 
     where fp.id = fr.id) 
     group by fruit_id, fruit_prop_Id 
+0

是的,你是对的,我很新的SQL,这是一个马虎做一个。其实查询已经是一个嵌套选择,我希望避免另一个。什么会提供最好的性能,我的解决方案与2选择或你的日期检查更好,但与3? –

+0

虽然客户端使用这个特定的SQL确保它是一个日期输入:) –

+0

不要害怕嵌套选择。他们不(必然)暗示更糟的表现(它只是一个观点)。 oracle可以并且会在内部重写查询。你会发现嵌套select与原始查询一样。 – DazzaL

1

你可以把日期检查在where子句中:

select 
    fp.id, 
    fr.id, 
    sum(case when and fp.result <> 'E' then 1 else 0 end) total, 
    sum(case when fp.result = 'G' then 1 else 0 end) colorgreen, 
    sum(case when fp.resultat = 'R' then 1 else 0 end) colorred 
FROM 
    fruit_properties fp, fruit fr 
WHERE 
    fp.id = fr.id 
    AND to_date(fp.offered_date) >= :ad_startdate 
    AND to_date(fp.offered_date) <= :ad_enddate 
GROUP BY 
    fp.id, fr.id 

编辑:在评论中指出,该查询会过滤掉不具有在给定的时间间隔任何要约日期标识。

+0

为你筛选出的行,这将改变他的回答。 – DazzaL

+0

即使你的答案帮助我,我不能应用它,因为我不能过滤出日期,这会给我很坏的结果 –