SQL語法如何將直的資料做橫向的字串連結 |
尚未結案
|
cindyliu
一般會員 發表:16 回覆:18 積分:6 註冊:2008-09-17 發送簡訊給我 |
請問各位~
這是一份類用明細表 欄位有費用類別、費用代碼、金額、備註.... TYPE CHG_CD AMT REMARK ------- --------------- --------- ---------------- 01 1004 250 abcd 02 1210 200 test 01 1005 100 01 1003 150 xyz 02 1221 100 ijk 03 1010 100 efg 這是依費用類別加總,最後產出來的樣子~ TYPE AMT REMARK ------- ---------- --------------------- 01 500 abcd、xyz 02 300 test、ijk 03 100 efg 因為前輩寫的FUNCTION是要傳入一段SQL語法去產出檔案... 目前加總的部分我OK,,, 卡在備註REMARK的地方,SQL要怎麼寫才能達到上面的結果? 請各位高手幫幫忙...感恩^^ 補充一下.. 因為公司有MSSQL與ORACLE,希望也能有ORACLE的寫法喔... (目前是ORACLE 比較急需用到) 謝謝^^ |
st33chen
尊榮會員 發表:15 回覆:591 積分:1201 註冊:2005-09-30 發送簡訊給我 |
您好, 1. 由 sql 產生的話要看用什麼資料庫,
mysql 直接用 group_concat (例 : select ....., group_concat(...) from ... ) oracle 的話, 請參考 http://delphi.ktop.com.tw/board.php?cid=30&fid=1498&tid=96292 2. 由 sql 產生資料後再後製作的方法的話, 也參考上列這一篇.
------
IS IT WHAT IT IS 我是 李慕白 請倒著唸. 又想把老話拿出來說, 請用台語發音 : 專家專家全是ROBOT CAR (滷肉腳啦); 都已接手這麼久了, 績效還是那麼爛, 講話還那麼大聲. |
careychen
尊榮會員 發表:41 回覆:580 積分:959 註冊:2004-03-03 發送簡訊給我 |
HI, 除了 st33chen 前輩的兩種方式外,這邊小弟再加一個 MSSQL 呼叫 Function 的方式
以您的 Sample 的話,請建立一個 function 在 SQL Server 裡面 [code sql] Create function StringAdd( @TYPE nvarchar(200) -- 這個 Size 或型態請依您自己的欄位設定 ) Returns nvarchar(4000) AS BEGIN Declare @sTmp nvarchar(4000) ; Set @sTmp=''; Select @sTmp=@sTmp '、' IsNull(Remark, '') from 類用明細表 where Type=@TYPE; Return Stuff(@sTmp, 1, 1, ''); END [/code] 然後寫下面這段 SQL 語法時,就可以寫成 [code sql] Select Type, Sum(AMT) as AMT, dbo.StringAdd(Type) as Remark from 類用明細表 Group by Type [/code] ===================引 用 cindyliu 文 章=================== 請問各位~ 這是一份類用明細表 欄位有費用類別、費用代碼、金額、備註.... TYPE CHG_CD AMT REMARK ------- --------------- --------- ---------------- 01 1004 250 abcd 02 1210 200 test 01 1005 100 01 1003 150 xyz 02 1221 100 ijk 03 1010 100 efg 這是依費用類別加總,最後產出來的樣子~ TYPE AMT REMARK ------- ---------- --------------------- 01 500 abcd、xyz 02 300 test、ijk 03 100 efg 因為前輩寫的FUNCTION是要傳入一段SQL語法去產出檔案... 目前加總的部分我OK,,, 卡在備註REMARK的地方,SQL要怎麼寫才能達到上面的結果? 請各位高手幫幫忙...感恩^^
------
價值的展現,來自於你用哪一個角度來看待它!! |
st33chen
尊榮會員 發表:15 回覆:591 積分:1201 註冊:2005-09-30 發送簡訊給我 |
再參一腳, 留下記錄當作筆記
mssql 模擬 group_concat 的另一方法 select Type, substr(RestaurantNames,1,len(RestaurantNames)-1) RestaurantNames from Restaurant AS A CROSS APPLY ( SELECT RestaurantName ',' FROM Restaurant AS B WHERE A.Type = B.Type FOR XML PATH('') ) D (RestaurantNames) GROUP BY Type, RestaurantNames
------
IS IT WHAT IT IS 我是 李慕白 請倒著唸. 又想把老話拿出來說, 請用台語發音 : 專家專家全是ROBOT CAR (滷肉腳啦); 都已接手這麼久了, 績效還是那麼爛, 講話還那麼大聲. |
careychen
尊榮會員 發表:41 回覆:580 積分:959 註冊:2004-03-03 發送簡訊給我 |
不好意思,說明一下請 st33chen 前輩見諒
使用 Xml 時,如果那個欄位裡有些較特殊的符號時,例如 > < & .... 時會被強制轉變成 http 的那種 Style 例如: > 變 &gt < 變 &lt & 變 &amp 所以在使用時請注意一下,另再說明一下,原本的寫法會有效能上的問題,因此如要使用 XML Path 時, 請改成如下的寫法 [code sql] Select Type, SubStr(RestaurantNames, 1, Len(RestaurantNames)-1) RestaurantNames from ( Select Type from Restaurant Group by Type ) AS A CROSS APPLY ( SELECT RestaurantName ',' FROM Restaurant AS B WHERE A.Type = B.Type FOR XML PATH('') ) D (RestaurantNames) [/code] ===================引 用 st33chen 文 章=================== 再參一腳, 留下記錄當作筆記 mssql 模擬 group_concat 的另一方法 select Type, substr(RestaurantNames,1,len(RestaurantNames)-1) RestaurantNames from Restaurant AS A CROSS APPLY ( SELECT RestaurantName ',' FROM Restaurant AS B WHERE A.Type = B.Type FOR XML PATH('') ) D (RestaurantNames) GROUP BY Type, RestaurantNames
------
價值的展現,來自於你用哪一個角度來看待它!!
編輯記錄
careychen 重新編輯於 2008-12-12 15:35:53, 註解 無‧
|
cindyliu
一般會員 發表:16 回覆:18 積分:6 註冊:2008-09-17 發送簡訊給我 |
st33chen 您好~
我用了你提供的網址裡的這SQL語法是我要的結果... 但是少了條件,我該怎麼套用到我的SQL條件裡呢? 「???」的條件的需要等於最外層的DN_NO與DATA_NO SELECT A.DN_NO, A.DN_DATE, B.DATA_NO, A.CUSTOM_NO, ( Select Substr(Sys_Connect_By_Path(REMARK, '、'), 2) From (Select Rownum Rid, Rownum 1 Next_Rid, REMARK From CHG Where ??? ) Where Rid = (Select Count(*) From CHG Where ???) Start With Rid = 1 Connect By Prior Next_Rid = Rid ) REMARK_2 FROM DEBTM A, CHG B WHERE (A.DN_NO=B.DN_NO) AND A.CUSTOM_NO ='A001' |
st33chen
尊榮會員 發表:15 回覆:591 積分:1201 註冊:2005-09-30 發送簡訊給我 |
您好,
我用您下列的例子實測出來的 sql 如下, 其中, type 欄名改為 tp, remark 欄名改為 remarks (再次呼籲一下, 欄名不要用 可能的保留字) : with data as ( select tp, remarks, row_number() over (partition by tp order by tp, remarks) rn, count(*) over (partition by tp) cnt from ktop ) select data.tp, amt, ltrim(sys_connect_by_path(remarks,','),',') remarks from data, ( select tp, sum(amt) amt from ktop group by tp ) b where rn = cnt and data.tp=b.tp start with rn = 1 connect by prior data.tp = data.tp and prior rn = rn-1 order by data.tp 參考一下 ======================================================== 補充一下, 我自己測試的結果, 認為, 還是用我在上述連結網頁中提到的建 oracle function 的方法比較好 因為 function 只要建一次, 以後都可在不同的情況下呼叫使用, 比較不用每次不一樣情況都要 花很多腦筋去結構 sql. 只要建一次的 oracle function 如下; CREATE OR REPLACE FUNCTION matrix (query_in in VARCHAR2) RETURN VARCHAR2 IS incoming varchar2(4000); hold_result varchar2(4000); c sys_refcursor; Begin open c for query_in; loop fetch c into incoming; exit when c%notfound; hold_result := hold_result||','||incoming; end loop; return ltrim(hold_result,','); END; / 而適用本次例子的 呼叫 sql 如下: select tp, sum(amt) amt, matrix('select remarks from ktop where tp=' || tp ) remarks from ktop group by tp 這樣的用法真的就比較接近 mysql 直接把 group_concat 放在 select 子句裏的樣子, 比較直觀. 同理, mssql 部份, 若 careychen 大大能把 mssql 的 那個 function 改成通用型(即不在 function 中寫死哪個 table 哪個 field) 的話, 那是最好不過的. 我工作環境無 mssql, 對 mssql 不熟 (也不喜歡 m.$oft), 所以 mssql 部份我幫不上忙 感恩啦. ===================引 用 cindyliu 文 章=================== 請問各位~ 這是一份類用明細表 欄位有費用類別、費用代碼、金額、備註.... TYPE CHG_CD AMT REMARK ------- --------------- --------- ---------------- 01 1004 250 abcd 02 1210 200 test 01 1005 100 01 1003 150 xyz 02 1221 100 ijk 03 1010 100 efg 這是依費用類別加總,最後產出來的樣子~ TYPE AMT REMARK ------- ---------- --------------------- 01 500 abcd、xyz 02 300 test、ijk 03 100 efg 因為前輩寫的FUNCTION是要傳入一段SQL語法去產出檔案... 目前加總的部分我OK,,, 卡在備註REMARK的地方,SQL要怎麼寫才能達到上面的結果? 請各位高手幫幫忙...感恩^^ 補充一下.. 因為公司有MSSQL與ORACLE,希望也能有ORACLE的寫法喔... (目前是ORACLE 比較急需用到) 謝謝^^
------
IS IT WHAT IT IS 我是 李慕白 請倒著唸. 又想把老話拿出來說, 請用台語發音 : 專家專家全是ROBOT CAR (滷肉腳啦); 都已接手這麼久了, 績效還是那麼爛, 講話還那麼大聲. |
本站聲明 |
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。 2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。 3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇! |