2010-02-15 39 views
2

我想在T-SQL(SQL Server 2000/2005)和PL/SQL(Oracle 10g)中使用基本相同的查詢。雖然它不是微不足道的,但它是合理的香草代碼,但它在SQL Server中工作,但在Oracle中失敗。我的目標是爲特定字段的每個唯一大小寫組合生成一行計數,省略任何只有一個此類組合的字段值。例如,該示例輸出指示令牌「兩個詞」以大寫/小寫的四種不同組合出現,最普遍的用法是全大寫版本(121個這樣的行)。Vanilla SQL與相關子查詢在T-SQL中工作,在PL/SQL中失敗

 
    alias  rows affected 
    phrase   25 
    Phrase   3 
    Two words  12 
    Two Words   9 
    TWO words   3 
    TWO WORDS  121 

提醒一下,SQL Server是不區分大小寫默認所以COLLATE子句讓我與它的工作大小寫敏感。另一方面,Oracle不需要按摩,因爲它區分大小寫。

該查詢T-SQL中工作正常:

select 
    description COLLATE SQL_Latin1_General_CP1_CS_AS as alias, 
    count(*) as "Rows Affected" 
from dbo.svcs t1 (nolock) 
where (
    select count(upper(alias)) as "Variation Count" 
    from 
    (-- list of unique spellings for each alias 
     select 
      description COLLATE SQL_Latin1_General_CP1_CS_AS as alias, 
      count(*) as count 
     from dbo.svcs (nolock) 
     where description = t1.description 
     group by description COLLATE SQL_Latin1_General_CP1_CS_AS 
    ) combos 
    group by upper(alias) 
    having count(upper(alias)) > 1 
) > 1 
group by description COLLATE SQL_Latin1_General_CP1_CS_AS 
order by description COLLATE SQL_Latin1_General_CP1_CS_AS 

該查詢在Oracle中失敗;它不承認外參考,抱怨,它使用一個「無效的標識符」:

select alias, count(*) as "Rows Affected" 
from dev1.svcs t1 
where (
    select count(upper(alias)) as "Variation Count" 
    from 
    (-- list of unique spellings for each alias 
     select alias, count(*) as count 
     from dev1.svcs 
     where upper(alias) = upper(t1.alias)  -- <<<<< Does not like outer reference to 't1.alias' here 
     group by alias 
    ) combos 
    group by upper(alias) 
    having count(upper(alias)) > 1 
) > 1 
group by alias 
order by alias 

那麼有沒有爲Oracle PL/SQL解決方法?

2010年2月16日更新

在我的整個數據集的測試後,我接受了加里的答案。他淘汰了相關的子查詢,以獲得更緊湊的解決方案,這是很好的,但我仍然好奇爲什麼相關的子查詢嘗試失敗,如果有人碰巧有這個想法...

+0

的Oracle SQL只處理一個別名級深。我無法從快速搜索中看到這些記錄,但恐怕就是這樣。 (這與PL/SQL btw無關 - 我冒昧地刪除了該標籤。) – 2016-01-26 14:47:09

回答

2

我想你可能會逃脫

select alias, upper(alias), count(*) cnt_alias 
from svcs m 
where upper(alias) in 
    (select upper(alias) up_a 
    from svcs 
    group by upper(alias) 
    having count(distinct alias) > 1) 
group by alias 
order by upper(alias), count(*) desc, alias; 

測試了:

create table svcs (id number, alias varchar2(10)); 

insert into svcs select level, 'phrase' from dual connect by level <= 25; 
insert into svcs select level, 'Phrase' from dual connect by level <= 3; 
insert into svcs select level, 'Two words' from dual connect by level <= 12; 
insert into svcs select level, 'Two Words' from dual connect by level <= 9; 
insert into svcs select level, 'TWO words' from dual connect by level <= 3; 
insert into svcs select level, 'TWO WORDS' from dual connect by level <= 121; 
insert into svcs select level, 'Only' from dual connect by level <= 121; 
+0

Gary:您的Oracle查詢在我的完整數據集上成功運行 - 謝謝! 爲了完整起見,我遷移你的算法回到SQL Server,以及: 選擇 說明分頁SQL_Latin1_General_CP1_CS_AS作爲別名, 上(介紹), COUNT(*)從dbo.svcs我們 「受影響的行」(NOLOCK ) 其中 (選擇從dbo.svcs(NOLOCK描述 ) 組通過描述 具有計數(不同描述COLLATE SQL_Latin1_General_CP1_CS_AS)> 1) 組通過描述COLLATE SQL_Latin1_General_CP1_CS_AS,描述描述 爲了通過描述COLLATE SQL_Latin1_General_CP1_CS_AS – 2010-02-16 17:58:51