分析函數、窗口函數、開窗函數


整理一下

oracle、sqlserver、mysql三大數據庫用法不一樣。

ORACLE

開窗函數和分組函數

oracle開窗函數有很多,用的比較多的是over(...),一般是和order、partition by、row_number()、rank()、dense_rank()幾個函數一起使用

分析函數和聚合函數

非常相似,有一些函數是重名的。
  聚合函數用group by分組,每個分組返回一個統計值;  分析函數用partition by分組,並且每組、每行都可以返回一個統計值

  顯而易見的區別是,從返回結果上看:
  聚合后的記錄數可能會減少,因為它對數據源進行了group by操作,所以對結果是有影響的,即返回的結果里去掉聚合的列后,跟聚合前的結果不一樣
  而分析后的記錄數是不變的,因為它的作用僅僅在於分析,所以不會對結果有影響,即返回的結果里去掉分析的列后,跟分析前的結果是一樣的

使用說明

分析函數要與開窗函數(over())一起使用,使用形式為:分析函數() over()

  開窗函數(over())包含三個分析子句:
    分組子句(partition by)
    排序子句(order by)
    窗口子句(rows)

子句可以根據需要全部省略或部分省略。
over()
over(order by eage)
over(partition by esex)
over(partition by esex order by eage)


開窗函數里的"窗",即"窗口",表示分析函數分析時要處理的數據范圍
窗口子句除了rows方式的窗口,還包括range方式和滑動窗口

分組子句(partition by)

可以省略
    理解上和group by類似
省略分組子句,所以當前組的范圍為整個表的數據行

排序子句(order by)

可以省略
和普通orderby用法一樣。
開窗函數內的order by和sql語句中的order by的執行時機。
分析及開窗函數是在整個sql查詢結束后再進行的, 即sql語句的order by也會影響分析函數的執行結果。

窗口子句(rows)

可以省略
窗口子句(rows)不能單獨存在,必須有order by子句時才能出現
有order by時,有窗口子句(rows)
有order by時,無窗口子句(rows),則默認的窗口是unbounded preceding and current row,即當前組的第一行到當前行
無order by時,無窗口子句(rows),則默認的窗口是unbounded preceding and unbounded following,即整個組
    窗口子句(rows)的相關關鍵字:
    preceding:表示在...之前
      1 preceding:表示當前記錄的前1條記錄
      2 preceding:表示當前記錄的前2條記錄
      n preceding:表示當前記錄的前n條記錄
      unbounded preceding:不受控制的,無限的,
                 若無分組,則表示所有記錄的第1條記錄
                 若有分組,則表示分組后,組內的第1條記錄

    following:表示在...之后
      1 following:表示當前記錄的后一條記錄
      2 following:表示當前記錄的后兩條記錄
      n following:表示當前記錄的后n條記錄
      unbounded following:不受控制的,無限的,
                若無分組,則表示所有記錄的最后一條記錄
                若有分組,則表示分組后,組內的最后一條記錄

 

 

常見分析函數

  • count():統計分區中各組的行數,partition by 可選,order by 可選
  • sum():統計分區中記錄的總和,partition by 可選,order by 可選
  • avg():統計分區中記錄的平均值,partition by 可選,order by 可選
  • min()\max():統計分區中記錄的最小\大值,partition by 可選,order by 可選

以上4最基礎,和常見的groupby中使用一樣。

  • rank() over() :跳躍排序,並列后跳躍,partition by 可選,order by 必選
  • dense_rank() :連續排序,並列后連續,partition by 可選,order by 必選
  • row_number() over() :排序,無重復值,無並列順序號,partition by 可選,order by 必選

以上3個排名函數一般用來分組取topN等

  • lag() over() :取出前n行數據,partition by 可選,order by 必選;lead() over() :取出后n行數據,partition by 可選,order by 必選

lead三個參數:第一個為hive列,第二個為取往后第幾行,第三個為取不到時默認值,lag與lead剛好相反,取前面的某行;
這兩個函數通常用來計算頁面停留時間,同比環比增長率等

  • first_value() over() :取出分區中第一條記錄的字段值,partition by 可選,order by 可選;last_value() over() :取出分區中最后一條記錄的字段值,partition by 可選,order by 可選
  • first :從DENSE_RANK返回的集合中取出排在最前面的一個值的行;last :從DENSE_RANK返回的集合中取出排在最后面的一個值的行

max(ccc) keep(dense_rank first order by bbb desc) over(partition by aaa)
按aaa分組,取bbb第一的記錄的,ccc最大值。

  • ntile(n) over() :partition by 可選,order by 必選

n表示將分區內記錄平均分成n份,多出的按照順序依次分給前面的組

 參考資料

https://blog.csdn.net/ZZQHELLO2018/article/details/105563517
https://www.cnblogs.com/shiliye/p/12363300.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM