因為要使用SQL做一個立方體表,從各個不同的維度對數據進行統計。這樣可以有利於BI展示。但是針對多個條件需要如何組合查詢處對應的結果給前端;想了一下這需要使用到組合。
內容目錄
例如:針對一張表;表結構如下:
CREATE TABLE CZT_TEST (
`biz_key` varchar(100) COLLATE utf8mb4_general_ci NOT NULL COMMENT '主鍵編號',
`year` varchar(100) COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '年份',
`adm_div_id` varchar(200) COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '區划ID',
`adm_div_code` varchar(200) COLLATE utf8mb4_general_ci DEFAULT '' COMMENT '區划編碼',
`adm_div_name` varchar(200) COLLATE utf8mb4_general_ci DEFAULT '' COMMENT '區划名稱',
`agency_id` varchar(200) COLLATE utf8mb4_general_ci DEFAULT '' COMMENT '單位ID',
`agency_code` varchar(200) COLLATE utf8mb4_general_ci DEFAULT NULL COMMENT '單位編碼',
`agency_name` varchar(200) COLLATE utf8mb4_general_ci DEFAULT '' COMMENT '單位名稱'
) ENGINE=InnoDB CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci COMMENT='測試';
如何使用維度呢?
使用 year 和 admin_div_id 和 agency_id 這三個字段作為維度,可以看成三個維度,這三個維度可以單獨計算統計也可以組合計算統計,那算在一起會出多少中結果;使用Java方法進行排列組合
Java代碼如下:
package com.example.demo.controller;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
public class Test {
public static void main(String[] args) {
// 年份
List<String> list001 = new ArrayList<>();
list001.add("2021,");
list001.add("2020,");
// 區划
List<String> list002 = new ArrayList<>();
list002.add("460100000,"); // 海口市
list002.add("460200000,"); // 三亞市
list002.add("460300000,"); // 三沙市
// 單位ID
List<String> list003 = new ArrayList<>();
list003.add("Agency_001,"); // 單位1
list003.add("Agency_002,"); // 單位2
list003.add("Agency_003,"); // 單位3
list003.add("Agency_004,"); // 單位4
list003.add("Agency_005,"); // 單位5
list003.add("Agency_006,"); // 單位6
// A.如果是完全組合的話方法如下
List<String> resultList = list001.stream().flatMap(str -> list002.stream().map(str::concat))
.flatMap(str -> list003.stream().map(str::concat)).collect(Collectors.toList());
// A.1具體多少種組合
System.out.println("============>>(list001,list002,list003)組合共:" + resultList.size() +" 種");
// A.2組合中都有啥
resultList.forEach(x -> {
System.out.println(x);
});
/**
* 不完全組合list001,list002,list003,(list001,list002),(list001,list003)
* ,(list002,list003),(list001,list002,list003)
* B.單個列表組合不用計算直接明顯list001,list002,list003
* B.1兩兩組合計算(list001,list002),(list001,list003),(list002,list003)
*/
// (list001,list002)組合
List<String> resultList12 = list001.stream().flatMap(str -> list002.stream().map(str::concat))
.collect(Collectors.toList());
// 具體多少種組合
System.out.println("============>>(list001,list002)組合共:" + resultList12.size() +" 種");
// 組合中都有啥
resultList12.forEach(x -> {
System.out.println(x);
});
// (list001,list003)組合
List<String> resultList13 = list001.stream().flatMap(str -> list003.stream().map(str::concat))
.collect(Collectors.toList());
// 具體多少種組合
System.out.println("============>>(list001,list003)組合共:" + resultList13.size() +" 種");
// 組合中都有啥
resultList13.forEach(x -> {
System.out.println(x);
});
// (list002,list003)組合
List<String> resultList23 = list002.stream().flatMap(str -> list003.stream().map(str::concat))
.collect(Collectors.toList());
// 具體多少種組合
System.out.println("============>>(list002,list003)組合共:" + resultList23.size() +" 種");
// 組合中都有啥
resultList23.forEach(x -> {
System.out.println(x);
});
}
}
執行結果如下
============>>(list001,list002,list003)組合共:36 種
2021,460100000,Agency_001,
2021,460100000,Agency_002,
2021,460100000,Agency_003,
2021,460100000,Agency_004,
2021,460100000,Agency_005,
2021,460100000,Agency_006,
2021,460200000,Agency_001,
2021,460200000,Agency_002,
2021,460200000,Agency_003,
2021,460200000,Agency_004,
2021,460200000,Agency_005,
2021,460200000,Agency_006,
2021,460300000,Agency_001,
2021,460300000,Agency_002,
2021,460300000,Agency_003,
2021,460300000,Agency_004,
2021,460300000,Agency_005,
2021,460300000,Agency_006,
2020,460100000,Agency_001,
2020,460100000,Agency_002,
2020,460100000,Agency_003,
2020,460100000,Agency_004,
2020,460100000,Agency_005,
2020,460100000,Agency_006,
2020,460200000,Agency_001,
2020,460200000,Agency_002,
2020,460200000,Agency_003,
2020,460200000,Agency_004,
2020,460200000,Agency_005,
2020,460200000,Agency_006,
2020,460300000,Agency_001,
2020,460300000,Agency_002,
2020,460300000,Agency_003,
2020,460300000,Agency_004,
2020,460300000,Agency_005,
2020,460300000,Agency_006,
============>>(list001,list002)組合共:6 種
2021,460100000,
2021,460200000,
2021,460300000,
2020,460100000,
2020,460200000,
2020,460300000,
============>>(list001,list003)組合共:12 種
2021,Agency_001,
2021,Agency_002,
2021,Agency_003,
2021,Agency_004,
2021,Agency_005,
2021,Agency_006,
2020,Agency_001,
2020,Agency_002,
2020,Agency_003,
2020,Agency_004,
2020,Agency_005,
2020,Agency_006,
============>>(list002,list003)組合共:18 種
460100000,Agency_001,
460100000,Agency_002,
460100000,Agency_003,
460100000,Agency_004,
460100000,Agency_005,
460100000,Agency_006,
460200000,Agency_001,
460200000,Agency_002,
460200000,Agency_003,
460200000,Agency_004,
460200000,Agency_005,
460200000,Agency_006,
460300000,Agency_001,
460300000,Agency_002,
460300000,Agency_003,
460300000,Agency_004,
460300000,Agency_005,
460300000,Agency_006,
如何使用呢
自動保存
把這些List通過','切割開來,然后使用SQL,根據不同的條件進行查詢
比如:
select * from year='2021' and adm_div_id='460100000' and agency_id='Agency_002'
這只是組合條件查詢出來的一種結果。
其他維度也可以,比如2個條件
select * from year='2021' and adm_div_id='460100000'
使用Python有更好的方法
因為Python3中有內置的排列組合函數
python內置函數-排列組合函數:
具體用法可以查詢Python3的API
product 笛卡爾積 (有放回抽樣排列)
permutations 排列 (不放回抽樣排列)
combinations 組合,沒有重復 (不放回抽樣組合)
combinations_with_replacement 組合,有重復 (有放回抽樣組合)