自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

如何用Pivot實(shí)現(xiàn)行列轉(zhuǎn)換

數(shù)據(jù)庫(kù) Oracle
在Oracle中,如果要實(shí)現(xiàn)行列轉(zhuǎn)換,較為常見(jiàn)的是用DECODE和CASE語(yǔ)句。對(duì)于簡(jiǎn)單的行列轉(zhuǎn)行,DECODE和CASE語(yǔ)句尚能應(yīng)付。在邏輯比較復(fù)雜,分組聚合較多的場(chǎng)景中,DECODE和CASE語(yǔ)句則力有不逮。而pivot則可完美解決這一切。

   首先,我們來(lái)看看Oracle對(duì)于其的解釋:

 

  可見(jiàn),pivot是數(shù)據(jù)倉(cāng)庫(kù)中的關(guān)鍵技術(shù),它利用交叉查詢(crosstabulation query)將行轉(zhuǎn)換為列。

  基本語(yǔ)法如下:

 

  1. SELECT .... 
  2. FROM <table-expr> 
  3.    PIVOT 
  4.      ( 
  5.       aggregate-function(<column>) 
  6.       FOR <pivot-columnIN (<value1>, <value2>,..., <valuen>) 
  7.         ) AS <alias> 
  8. WHERE ..... 

 

  下面我們來(lái)通過(guò)具體的案例對(duì)其進(jìn)行闡述。

  首先,構(gòu)造案例所需的數(shù)據(jù),

  1> 創(chuàng)建視圖,以EMP表的數(shù)據(jù)作為源數(shù)據(jù)。

 

  1. CREATE VIEW emp_view AS 
  2. SELECT 
  3.  deptno,job,to_char(hiredate,'yyyy') hiredate, 
  4.  count(*) cnt,sum(sal) sum_sal 
  5. FROM emp 
  6. GROUP BY deptno,job,to_char(hiredate,'yyyy'); 

 

  其中,deptno為部門(mén)號(hào),job為工作的類(lèi)型(即工種),hiredate為雇傭的日期,cnt為特定部門(mén),特定工種在特定年份雇傭的員工的總數(shù),sum_sal為特定部門(mén),特定工種,特定年份雇傭的員工的工資的總和。

  2> 視圖的數(shù)據(jù)如下:

 

  1. SQL> select * from emp_view; 
  2.  
  3.     DEPTNO JOB       HIRE        CNT    SUM_SAL 
  4. ---------- --------- ---- ---------- ---------- 
  5. CLERK     1980          1        800 
  6. ANALYST   1981          1       3000 
  7. ANALYST   1987          1       3000 
  8. CLERK     1981          1        950 
  9. MANAGER   1981          1       2850 
  10. MANAGER   1981          1       2450 
  11. SALESMAN  1981          4       5600 
  12. MANAGER   1981          1       2975 
  13. PRESIDENT 1981          1       5000 
  14. CLERK     1982          1       1300 
  15. CLERK     1987          1       1100 
  16. rows selected. 

 

  應(yīng)用場(chǎng)景一:

  基本的Pivot轉(zhuǎn)換

  例1:

 

  1. SELECT * FROM 
  2. SELECT deptno,hiredate,cnt 
  3.   FROM emp_view 
  4.  ) PIVOT (SUM(cnt) 
  5.    FOR hiredate IN ('1980' AS "1980",'1981' AS "1981"
  6.                     '1982' AS "1982",'1987' AS "1987")) 
  7. ORDER BY deptno; 
  8.  
  9.     DEPTNO       1980       1981       1982       1987 
  10. ---------- ---------- ---------- ---------- ---------- 
  11.                     2          1 
  12.          1          2                     2 
  13.                     6 
  14. rows selected. 

 

  例2:

 

  1. SELECT * FROM 
  2. SELECT deptno,job,cnt 
  3.   FROM emp_view 
  4.  ) PIVOT (SUM(cnt) 
  5.    FOR job IN ('CLERK','ANALYST','MANAGER','SALESMAN','PRESIDENT')) 
  6. ORDER BY deptno; 
  7.  
  8.     DEPTNO    'CLERK'  'ANALYST'  'MANAGER' 'SALESMAN' 'PRESIDENT' 
  9. ---------- ---------- ---------- ---------- ---------- ----------- 
  10.          1                     1                      1 
  11.          2          2          1 
  12.          1                     1          4 
  13. rows selected. 

 

  兩例以不同的列進(jìn)行統(tǒng)計(jì),前者是hiredate,后者是job。

  除此之外,前者用了別名,后面沒(méi)有用別名,兩者的顯示效果也是不一樣的。

  應(yīng)用場(chǎng)景二:

  對(duì)多列進(jìn)行Pivot轉(zhuǎn)換

 

  1. SELECT * FROM 
  2. SELECT deptno,job,hiredate,cnt 
  3.   FROM emp_view 
  4.  ) PIVOT (SUM(cnt) 
  5.             FOR (job,hiredate) IN 
  6.               (('CLERK','1980'AS clerk_1980, 
  7.                ('CLERK','1981'AS clerk_1981, 
  8.                ('ANALYST','1987'AS analyst_1987, 
  9.                ('MANAGER','1981'AS manager_1981 
  10.               ) 
  11.            ) 
  12. ORDER by deptno; 
  13.  
  14.     DEPTNO CLERK_1980 CLERK_1981 ANALYST_1987 MANAGER_1981 
  15. ---------- ---------- ---------- ------------ ------------ 
  16.                                               1 
  17.          1                       1            1 
  18.                     1                         1 
  19. rows selected. 

 

  限于篇幅,F(xiàn)OR (job,hiredate) IN語(yǔ)句中沒(méi)有列出更多組合,只列出了四組,當(dāng)然,我們可以根據(jù)實(shí)際場(chǎng)景需要羅列更多的組合。

  從本例中可以看出,對(duì)兩個(gè)列進(jìn)行Pivot轉(zhuǎn)換可從三個(gè)維度呈現(xiàn)統(tǒng)計(jì)結(jié)果。

  應(yīng)用場(chǎng)景三:

  用Pivot實(shí)現(xiàn)多個(gè)聚合

 

  1. SELECT * FROM 
  2. SELECT deptno,hiredate,cnt,sum_sal 
  3.   FROM emp_view 
  4.  ) PIVOT ( SUM(cnt) AS cnt, 
  5.            SUM(sum_sal) AS sum_sal 
  6.            FOR hiredate IN ('1980','1981','1982','1987')) 
  7. ORDER BY deptno; 
  8.  
  9.     DEPTNO '1980'_CNT '1980'_SUM_SAL '1981'_CNT '1981'_SUM_SAL '1982'_CNT '1982'_SUM_SAL '1987'_CNT '1987'_SUM_SAL 
  10. ---------- ---------- -------------- ---------- -------------- ---------- -------------- ---------- -------------- 
  11.                                    2           7450          1           1300 
  12.          1            800          2           5975                                    2           4100 
  13.                                    6           9400 
  14. rows selected. 

 

  '1981'_CNT指的是1981年雇傭的員工的總數(shù),'1981'_SUM_SAL指的是1981年雇傭員工所開(kāi)出的工資。

  具體到本例中,即1981年10號(hào)部門(mén)招聘了2位員工,開(kāi)出的工資合計(jì)為7450元,20號(hào)部門(mén)招聘了2位員工,開(kāi)出的工資合計(jì)為5975元,30號(hào)部門(mén)招聘了6名員工,開(kāi)出的工資合計(jì)為9400元,依次類(lèi)推。

  既然有pivot將行轉(zhuǎn)換為列,同樣也有unpivot操作將聚合后的列轉(zhuǎn)換為行。

  UNPIVOT

  以上述應(yīng)用場(chǎng)景三的結(jié)果作為源數(shù)據(jù)進(jìn)行操作

 

  1. CREATE TABLE T1 AS 
  2. SELECT * FROM 
  3. SELECT deptno,hiredate,cnt,sum_sal 
  4.   FROM emp_view 
  5.  ) PIVOT ( SUM(cnt) AS cnt, 
  6.            SUM(sum_sal) AS sum_sal 
  7.            FOR hiredate IN ('1980' AS "1980",'1981' AS "1981"
  8.                             '1982' AS "1982",'1987' AS "1987")) 
  9. ORDER BY deptno 

 

  表T1的結(jié)果為:

 

  1. SQL> select * from t1; 
  2.  
  3.     DEPTNO   1980_CNT 1980_SUM_SAL   1981_CNT 1981_SUM_SAL   1982_CNT 1982_SUM_SAL   1987_CNT 1987_SUM_SAL 
  4. ---------- ---------- ------------ ---------- ------------ ---------- ------------ ---------- ------------ 
  5.                                  2         7450          1         1300 
  6.          1          800          2         5975                                  2         4100 
  7.                                  6         9400 
  8. rows selected. 

 

  首先進(jìn)行一維unpivot

 

  1. SELECT deptno,DECODE(hiredate,'1980_CNT','1980','1981_CNT','1981','1982_CNT','1982','1987_CNT','1987'AS hiredate,cnt 
  2. FROM T1 
  3. UNPIVOT INCLUDE NULLS 
  4. ( cnt 
  5.   FOR hiredate IN ("1980_CNT","1981_CNT","1982_CNT","1987_CNT")); 
  6.  
  7.     DEPTNO HIRE        CNT 
  8. ---------- ---- ---------- 
  9. 1980 
  10. 1981          2 
  11. 1982          1 
  12. 1987 
  13. 1980          1 
  14. 1981          2 
  15. 1982 
  16. 1987          2 
  17. 1980 
  18. 1981          6 
  19. 1982 
  20. 1987 
  21. rows selected. 

 

  輸出的結(jié)果為不同部門(mén)在不同年份的雇傭人數(shù),

  注意:上述SQL語(yǔ)句中UNPIVOT后加了INCLUDE NULLS,當(dāng)然也可以指定為EXCLUDE NULLS,即排除cnt為空的值,如果不指定,則默認(rèn)為EXCLUDE NULLS。

  UNPIVOT后不指定INCLUDE NULLS的輸入結(jié)果為:

 

  1. DEPTNO HIRE        CNT 
  2. ---------- ---- ---------- 
  3. 1981          2 
  4. 1982          1 
  5. 1980          1 
  6. 1981          2 
  7. 1987          2 
  8. 1981          6 
  9. rows selected. 

 

  下面,我們?cè)龠M(jìn)行二維unpivot

 

  1. SELECT deptno,hiredate,cnt,sum_sal 
  2. FROM T1 
  3. UNPIVOT 
  4. ( (cnt,sum_sal) 
  5.   FOR hiredate IN (("1980_CNT","1980_SUM_SAL"AS 1980, 
  6.                    ("1981_CNT","1981_SUM_SAL"AS 1981, 
  7.                    ("1982_CNT","1982_SUM_SAL"AS 1982, 
  8.                    ("1987_CNT","1987_SUM_SAL"AS 1987)); 
  9.  
  10.     DEPTNO   HIREDATE        CNT    SUM_SAL 
  11. ---------- ---------- ---------- ---------- 
  12.       1981          2       7450 
  13.       1982          1       1300 
  14.       1980          1        800 
  15.       1981          2       5975 
  16.       1987          2       4100 
  17.       1981          6       9400 
  18. rows selected. 

 

  輸入結(jié)果為T(mén)1表列轉(zhuǎn)行的結(jié)果。

  參考文檔:

  SQL for Analysis and Reporting

責(zé)任編輯:honglu 來(lái)源: 博客園
相關(guān)推薦

2011-07-15 09:04:42

PIVOTUNPIVOT

2024-05-17 08:52:43

SQL實(shí)用技巧行列轉(zhuǎn)換

2011-03-15 14:26:23

iptablesNAT

2010-03-04 15:24:14

Python程序

2011-03-15 09:10:47

iptablesNAT

2018-03-15 14:07:17

潤(rùn)乾Excel行列轉(zhuǎn)換

2020-05-09 10:38:31

Python透視表數(shù)據(jù)

2010-05-24 10:23:34

實(shí)現(xiàn)MySQL

2016-09-26 15:14:28

Javascript前端vue

2017-10-11 16:19:36

jquery留言框設(shè)計(jì)

2017-10-27 22:03:35

javascrip

2018-03-30 10:26:24

行間距行高iOS

2009-02-05 14:17:37

FTP服務(wù)器Java

2010-05-25 13:47:53

MySQL 命令

2021-03-02 10:57:39

二叉樹(shù)二叉堆節(jié)點(diǎn)

2017-04-26 08:31:10

神經(jīng)網(wǎng)絡(luò)自然語(yǔ)言PyTorch

2023-10-26 11:03:50

C語(yǔ)言宏定義

2018-08-31 09:55:38

Ansible網(wǎng)絡(luò)自動(dòng)化

2009-12-08 18:01:00

曙光移動(dòng)集中采購(gòu)

2015-07-06 13:36:14

Redis微博關(guān)注關(guān)系
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)