1. 程式人生 > >maxcompute 2.0複雜資料型別之array

maxcompute 2.0複雜資料型別之array

開發十年,就只剩下這套架構體系了! >>>   

1. 含義

類似於Java中的array。有序、可重複。

2. 場景

什麼樣的資料,適合使用array型別來儲存呢?這裡列舉了幾個我在開發中實際用到的場景。

2.1 標籤類的資料

為什麼說標籤類資料適合使用array型別呢?
(1)標籤一般是一個只有key、沒有value的結構;
(2)標籤的數量(列舉值個數)會非常多;
(3)標籤的變化會比較頻繁;
(4)標籤會過期;
因此,比起“建立多個欄位”、“使用指定分隔符分隔的字串”、“使用map”等方法,使用array是更合適的。

2.2 物件列表

物件有多種固定的屬性,簡單的key-value格式無法滿足,可以使用array巢狀struct的方式定義。減少了維護資料字典的工作量。

3. 玩轉array

3.1 陣列欄位拆成多行

3.1.1 explode

select explode(t.arr) from (select array('a','b','c') as arr) t;

col
a
b
c
select t1.id,t2.arr from (select 'xxx' as id,array('a','b','c') as arr) t1 lateral view explode(t1.arr) t2 as arr ;

id arr
xxx a
xxx b
xxx c

3.1.2 posexplode

select posexplode(t.arr) from (select array('a','b','c') as arr) t;

pos val
0 a
1 b
2 c
select t1.id,t2.serialno,t2.arr from (select 'xxx' as id,array('a','b','c') as arr) t1 lateral view posexplode(t1.arr) t2 as serialno,arr ;

id serialno arr
xxx 0 a
xxx 1 b
xxx 2 c

3.2 多行合併成陣列

3.2.1 不去重

select collect_list(t.c1) as arr from ( select 'a' as c1 union all select 'a' as c1 union all select 'b' as c1) t;

arr
["a","a","b"]

3.2.2 去重

select collect_set(t.c1) as arr from ( select 'a' as c1 union all select 'a' as c1 union all select 'b' as c1) t;

arr
["a","b"]

3.3 陣列拼成字串

select concat_ws(',',t.arr) from (select array('a','b','c') as arr) t;

_c0
a,b,c

3.4 字串轉成陣列

select split('a,b,c',',');

_c0
["a","b","c"]

3.5 構造陣列

select array('aa','bb','cc');

_c0
["aa","bb","cc"]

3.6 陣列元素排序

select sort_array(array('b','c','e','a','d'));

_c0
["a","b","c","d","e"]
select sort_array(array(1,10,100,2,3));

_c0
[1,2,3,10,100]

3.7 陣列中增加一項

select split(concat('d,',concat_ws(',',t.arr)),',') as arr from (select array('a','b','c') as arr) t;

arr
["d","a","b","c"]

4. 常見用法

4.1 代替無法使用的with cube

例如現在有張下單記錄流水錶,記錄著每一條下單記錄,包含欄位“訂單ID”、“下單人ID”、“下單渠道(網站/app)”。
現在要統計“各渠道的下單人數和訂單數”,渠道維度包含“不限”、“網站”、“APP”三項。
一般做這些包含“不限”的維度的聚合計算時,都使用group by xxx with cube關鍵字。但是maxcompute中暫時還不支援這個關鍵字,所以我們換另一種方法來實現。

SELECT tt.`下單渠道`, COUNT(1) AS `下單人數`, SUM(tt.`下單量`) AS `下單量`
FROM (
    SELECT t1.`下單人ID`, t2.`下單渠道`, SUM(t1.`下單量`) AS `下單量`
    FROM (
        SELECT t.`下單人ID`, t.`下單渠道`, SUM(t.`下單量`) AS `下單量`
        FROM (
            SELECT `訂單ID`, `下單人ID`, `下單渠道`, 1 AS `下單量`
            FROM `下單記錄流水錶`
        ) t
        GROUP BY t.`下單人ID`, 
            t.`下單渠道`
    ) t1
        LATERAL VIEW EXPLODE(array(t1.`下單渠道`, '不限')) t2 AS `下單渠道`
    GROUP BY t1.`下單人ID`, 
        t2.`下單渠道`
) tt
GROUP BY tt.`下單渠道`

4.2 陣列是否相等

陣列的相等或不等,無法通過“=”來判斷,因此要嘗試一些其他的方法。最常用的辦法,就是轉成字串再比較。

4.2.1 考慮順序是否一致

直接轉成字串後,比較是否相等

4.2.2 不考慮順序是否一致

先排序,再轉成字串,然後比較是否相等

 

原文連結
更多技術乾貨 請關注阿里云云棲社群微