K均值聚類首先隨機選擇K個對象作為每個簇的初始聚類中心,然后計算剩余對象與各簇中心的距離,將其分配至距離最近的簇,再重新計算每個簇的聚類中心。該算法假設聚類對象為空間向量,且以各聚類內部的均方誤差和最小為目標,不斷地進行計算迭代,直到準則函數收斂。
注意事項
使用K均值聚類組件時,您需要注意以下事宜:
如果使用夾角余弦距離,則某些聚類可能為空,即聚類數量小于K。因為初始化的K個中心點(向量)可能是平行向量,所以按順序遍歷中心點時,樣本不會被分配至后面的中心點(平行向量)。建議通過外部輸入中心表的方式,使用線下準備好的K個中心點。
如果輸入表中存在NULL或空值,則系統報錯
Algo Job Failed-System Error-Null feature value found
。建議使用默認值進行填充。使用稀疏格式數據作輸入時,如果最大列編號超過2,000,000,則系統報錯
Algo Job Failed-System Error-Feature count can't be more than 2000000
。建議從0或1開始,重新對列進行編號。如果中心點模型過大導致寫失敗,則系統報錯
Algo Job Failed-System Error-kIOError:Write failed for message: comparison_measure
。建議將稀疏矩陣的列從0或1開始,重新編號。如果模型規模col*centerCount>27,0000,000
,則只能通過命令行的方式,去除modelName參數,再重新執行聚類。如果輸入表的列名存在SQL關鍵字,則系統報錯
FAILED: Failed Task createCenterTable:kOtherError:ODPS-0130161:[1,558] Parse exception - invalid token ‘,’, expect ‘’)’’
。輸入表字段格式說明:參與訓練的數據列支持INT和DOUBLE數據類型。如果輸入為稀疏格式的表,則支持STRING類型的數據列。
組件配置
您可以使用以下任意一種方式,配置K均值聚類組件參數。
方式一:可視化方式
在Designer工作流頁面配置組件參數。
頁簽 | 參數 | 描述 |
字段設置 | 特征列 | 輸入數據表中,參與訓練的列。列名以半角逗號(,)分隔,支持INT和DOUBLE類型。如果輸入為稀疏格式,則支持STRING類型的列。 |
附加列 | 附加輸出至聚類結果表的輸入列,列名以半角逗號(,)分隔。 | |
輸入為稀疏矩陣 | 使用KV格式表示稀疏數據。 | |
kv鍵間分隔符 | 默認為半角逗號(,)。 | |
kv鍵內分隔符 | 默認為半角冒號(:)。 | |
參數設置 | 聚類數 | 取值范圍為1~1000。 |
距離度量方式 | 支持Euclidean、Cosine及Cityblock方式。 | |
質心初始化方法 | 支持Random、First K、Uniform、K-Means++及使用初始質心表方法。 | |
最大迭代次數 | 取值范圍為1~1000。 | |
收斂標準 | 迭代終止條件。 | |
初始隨機種子 | 默認值為當前時間。如果seed為固定值,則聚類結果穩定。 | |
執行調優 | 核心數 | 默認為系統自動分配。 |
每個核的內存大小 | 默認為系統自動分配,單位為MB。 |
方式二:PAI命令方式
使用PAI命令方式,配置該組件參數。您可以使用SQL腳本組件進行PAI命令調用,詳情請參見SQL腳本。
pai -name kmeans
-project algo_public
-DinputTableName=pai_kmeans_test_input
-DselectedColNames=f0,f1
-DappendColNames=f0,f1
-DcenterCount=3
-Dloop=10
-Daccuracy=0.01
-DdistanceType=euclidean
-DinitCenterMethod=random
-Dseed=1
-DmodelName=pai_kmeans_test_output_model_
-DidxTableName=pai_kmeans_test_output_idx
-DclusterCountTableName=pai_kmeans_test_output_couter
-DcenterTableName=pai_kmeans_test_output_center;
參數 | 是否必選 | 描述 | 默認值 |
inputTableName | 是 | 輸入表的表名。 | 無 |
selectedColNames | 否 | 輸入數據表中,參與訓練的列。列名以半角逗號(,)分隔,支持INT和DOUBLE類型。如果輸入為稀疏格式,則支持STRING類型的列。 | 所有列 |
inputTablePartitions | 否 | 輸入表中,參與訓練的分區。支持以下格式:
說明 如果指定多個分區,則使用半角逗號(,)分隔。 | 所有分區 |
appendColNames | 否 | 附加輸出至聚類結果表的輸入列,列名以半角逗號(,)分隔。 | 無 |
enableSparse | 否 | 輸入表是否為稀疏矩陣,取值為true或false。 | false |
itemDelimiter | 否 | KV對之間的分隔符。 | 半角逗號(,) |
kvDelimiter | 否 | key和value之間的分隔符。 | 半角冒號(:) |
centerCount | 是 | 聚類數,取值范圍為1~1000。 | 10 |
distanceType | 否 | 距離度量方式,支持以下類型:
| euclidean |
initCenterMethod | 否 | 質心初始化的方法,支持以下方法:
| random |
initCenterTableName | 否 | 初始質心表的名稱。如果initCenterMethod為external,則該參數生效。 | 無 |
loop | 否 | 最大迭代次數,取值范圍為1~1000。 | 100 |
accuracy | 否 | 算法終止條件。如果兩次迭代的目標差小于該值,則算法終止。 | 0.1 |
seed | 否 | 初始隨機種子。 | 當前時間 |
modelName | 否 | 輸出模型的名稱。 | 無 |
idxTableName | 是 | 輸出聚類結果表,包括聚類后每條記錄所屬的類號。 | 無 |
idxTablePartition | 否 | 聚類結果表的分區。 | 無 |
clusterCountTableName | 否 | 聚類統計表,統計各聚類包含的點數量。 | 無 |
centerTableName | 否 | 聚類中心表。 | 無 |
coreNum | 否 | 節點數量,與memSizePerCore搭配使用。取值范圍為1~9999。 | 系統自動分配 |
memSizePerCore | 否 | 每個節點的內存大小,取值范圍為1024 MB~64*1024 MB。 | 系統自動分配 |
lifecycle | 否 | 輸出表的生命周期,單位為天。 | 無 |
組件輸出
K均值聚類輸出聚類結果表、聚類統計表及聚類中心表。輸出格式如下:
聚類結果表
列名
描述
appendColNames
附加列。
cluster_index
訓練表中,每個樣本被分配到的簇。
distance
訓練表中,每個樣本到簇中心的距離。
聚類統計表
列名
描述
cluster_index
簇編號。
cluster_count
每個簇中的樣本數量。
聚類中心表
列名
描述
cluster_index
簇編號。
selectedColNames
訓練表中,參與訓練的列。
示例
以稠密格式數據作為輸入:
您可以通過以下任何一種方式,生成測試數據:
使用初始質心表的方式
create table pai_kmeans_test_init_center as select * from ( select 1 as f0,2 as f1 union all select 1 as f0,3 as f1 union all select 1 as f0,4 as f1 )tmp;
使用其他初始質心的方式
create table pai_kmeans_test_input as select * from ( select 'id1' as id,1 as f0,2 as f1 union all select 'id2' as id,1 as f0,3 as f1 union all select 'id3' as id,1 as f0,4 as f1 union all select 'id4' as id,0 as f0,3 as f1 union all select 'id5' as id,0 as f0,4 as f1 )tmp;
使用PAI命令,提交K均值聚類算法組件參數:
使用初始質心表的方式
drop table if exists pai_kmeans_test_output_idx; yes drop table if exists pai_kmeans_test_output_couter; yes drop table if exists pai_kmeans_test_output_center; yes drop offlinemodel if exists pai_kmeans_test_output_model_; yes pai -name kmeans -project algo_public -DinputTableName=pai_kmeans_test_input -DinitCenterTableName=pai_kmeans_test_init_center -DselectedColNames=f0,f1 -DappendColNames=f0,f1 -DcenterCount=3 -Dloop=10 -Daccuracy=0.01 -DdistanceType=euclidean -DinitCenterMethod=external -Dseed=1 -DmodelName=pai_kmeans_test_output_model_ -DidxTableName=pai_kmeans_test_output_idx -DclusterCountTableName=pai_kmeans_test_output_couter -DcenterTableName=pai_kmeans_test_output_center;
使用隨機初始質心的方式
drop table if exists pai_kmeans_test_output_idx; yes drop table if exists pai_kmeans_test_output_couter; yes drop table if exists pai_kmeans_test_output_center; yes drop offlinemodel if exists pai_kmeans_test_output_model_; yes pai -name kmeans -project algo_public -DinputTableName=pai_kmeans_test_input -DselectedColNames=f0,f1 -DappendColNames=f0,f1 -DcenterCount=3 -Dloop=10 -Daccuracy=0.01 -DdistanceType=euclidean -DinitCenterMethod=random -Dseed=1 -DmodelName=pai_kmeans_test_output_model_ -DidxTableName=pai_kmeans_test_output_idx -DclusterCountTableName=pai_kmeans_test_output_couter -DcenterTableName=pai_kmeans_test_output_center;
查看聚類結果表、聚類統計表及聚類中心表:
聚類結果表idxTableName
+------------+------------+---------------+------------+ | f0 | f1 | cluster_index | distance | +------------+------------+---------------+------------+ | 1 | 2 | 0 | 0.0 | | 1 | 3 | 1 | 0.5 | | 1 | 4 | 2 | 0.5 | | 0 | 3 | 1 | 0.5 | | 0 | 4 | 2 | 0.5 | +------------+------------+---------------+------------+
聚類統計表clusterCountTableName
+---------------+---------------+ | cluster_index | cluster_count | +---------------+---------------+ | 0 | 1 | | 1 | 2 | | 2 | 2 | +---------------+---------------+
聚類中心表centerTableName
+---------------+------------+------------+ | cluster_index | f0 | f1 | +---------------+------------+------------+ | 0 | 1.0 | 2.0 | | 1 | 0.5 | 3.0 | | 2 | 0.5 | 4.0 | +---------------+------------+------------+
以稀疏格式數據作為輸入:
生成測試數據。
create table pai_kmeans_test_sparse_input as select * from ( select 1 as id,"s1" as id_s,"0:0.1,1:0.2" as kvs0,"2:0.3,3:0.4" as kvs1 union all select 2 as id,"s2" as id_s,"0:1.1,2:1.2" as kvs0,"4:1.3,5:1.4" as kvs1 union all select 3 as id,"s3" as id_s,"0:2.1,3:2.2" as kvs0,"6:2.3,7:2.4" as kvs1 union all select 4 as id,"s4" as id_s,"0:3.1,4:3.2" as kvs0,"8:3.3,9:3.4" as kvs1 union all select 5 as id,"s5" as id_s,"0:5.1,5:5.2" as kvs0,"10:5.3,6:5.4" as kvs1 )tmp;
稀疏格式數據作為輸入時,使用0填充缺失的列。如果多個列同時作為輸入,則會被合并。例如,kvs0和kvs1同時作為輸入,則第一行的實際數據如下。
0:0.1,1:0.2,2:0.3,3:0.4,4:0,5:0,6:0,7:0,8:0,9:0,10:0
示例中的稀疏矩陣列從0開始編號,矩陣共5行11列。如果kvs中的某列包含
123456789:0.1
,則稀疏矩陣變為5行123456789列,該矩陣會消耗大量CPU和內存。對于kvs中存在異常列編號的原始數據,建議重新進行列編號以減小矩陣規模。使用PAI命令,提交K均值聚類組件的參數。
pai -name kmeans -project algo_public -DinputTableName=pai_kmeans_test_sparse_input -DenableSparse=true -DselectedColNames=kvs0,kvs1 -DappendColNames=id,id_s -DitemDelimiter=, -DkvDelimiter=: -DcenterCount=3 -Dloop=100 -Daccuracy=0.01 -DdistanceType=euclidean -DinitCenterMethod=topk -Dseed=1 -DmodelName=pai_kmeans_test_input_sparse_output_model -DidxTableName=pai_kmeans_test_sparse_output_idx -DclusterCountTableName=pai_kmeans_test_sparse_output_couter -DcenterTableName=pai_kmeans_test_sparse_output_center;
查看聚類結果表、聚類統計表及聚類中心表:
聚類結果表idxTableName
+------------+------------+---------------+------------+ | id | id_s | cluster_index | distance | +------------+------------+---------------+------------+ | 4 | s4 | 0 | 2.90215437218629 | | 5 | s5 | 1 | 0.0 | | 1 | s1 | 2 | 0.7088723439378913 | | 2 | s2 | 2 | 1.1683321445547923 | | 3 | s3 | 0 | 2.0548722588034516 | +------------+------------+---------------+------------+
聚類統計表clusterCountTableName
+---------------+---------------+ | cluster_index | cluster_count | +---------------+---------------+ | 0 | 2 | | 1 | 1 | | 2 | 2 | +---------------+---------------+
聚類中心表centerTableName
+---------------+------------+------------+ | cluster_index | kvs0 | kvs1 | +---------------+------------+------------+ | 0 | 0:2.6,1:0,2:0,3:1.1,4:1.6,5:0 | 6:1.15,7:1.2,8:1.65,9:1.7,10:0 | | 1 | 0:5.1,1:0,2:0,3:0,4:0,5:5.2 | 6:5.4,7:0,8:0,9:0,10:5.3 | | 2 | 0:0.6,1:0.1,2:0.75,3:0.2,4:0.65,5:0.7 | 6:0,7:0,8:0,9:0,10:0 | +---------------+------------+------------+