2013-03-14 21 views
1

我正在將存儲過程代碼從Oracle遷移到DB2,我需要找到一種測試數組成員資格的方法(Oracle有MEMBER OF運算符)。在DB2 SQL中測試數組成員資格PL

存儲過程除其他外還使用了一個用戶數組(通過JDBC從Java代碼接收的參數)。我想找到在數組中進行成員資格測試的最有效方法。使用Oracle,我會做:

FOR r IN (SELECT * FROM acls WHERE acls.id = curid) LOOP 
    IF r.user MEMBER OF users THEN 
    RETURN 1; 
    END IF; 
END LOOP; 

但是我沒有找到的MEMBER OF在DB2等價物:

FOR r AS SELECT * FROM acls WHERE acls.id = curid DO 
    IF r.user ????? users THEN 
    RETURN 1; 
    END IF; 
END FOR; 

我看到兩個選擇:

  1. 做一套內環的所有數組元素都可以「手動」進行測試。
  2. 不要使用數組,而是使用單個字符串並使用基於LIKE的模式匹配。

有沒有更好的方法?請記住,該數組來自外部代碼,不能作爲我可以JOIN或任何相關的表傳遞。

回答

0

您可以使用associative array(在DB2 9.7+中提供)和array_exists predicate執行此操作。我不確定這是否適用於正在通過的程序。我發現array_exists很慢。你用光標循環的一般設計也會很慢。

如果性能是一個問題,你很可能會更好做的這些事情,而不是一個:

  • 用戶的陣列投擲到一個臨時表的過程中,然後做一個正常的join到表找到匹配的記錄。
  • 使用動態SQL構造查詢(如in子句中。

下面是一些你可以使用動態SQL做榜樣。對於這個解決方案,具備Java送你一個字符串,分離用逗號:。

declare v_sql varchar(1000); --Bigger than maximum possible result query... 
declare stmt varchar(1000); 
declare return_result integer; 
set v_sql = 'select case when count(*) > 0 then 1 else 0 end' & 
    ' from acls WHERE acls.id = curid and user in (' & users & ')' & 
    ' group by (1)'; 
prepare stmt from v_sql; 
open mycur; 
fetch mycur into return_result; 
close mycur; 
return return_result; 

這是假定用戶是數值如果是字符串,這是行不通的,因爲每個用戶具有in子句中被引用

+0

謝謝,我想沒有什麼神奇然後回答。 – 2013-03-19 14:07:29