7.2 初始化类心

 

kmeans的聚类结果受随机初始化的类心影响较大,有可能两次聚类的结果会因为初始类心的不同而不同,这会造成一种奇怪的现象,同一天的数据,因为两次聚类而属于两条生产路线,这是工业生产中不能接受的。

想要避免随机初始化类心的影响,需要输入一个确定的成员作为kmeans聚类的初始化类心,从而保证聚类结果稳定,可是这个初始化类心怎么选择呢?

生产路线是需要分的类,只要从收率数据中找到各生产路线下一个典型的成员,把这些典型成员作为初始类心传给kmeans算法即可。什么样的成员才是生产路线下的典型成员呢?

生产路线的特点是相应的出料收率较大,而其他收率较小。根据这一特点,可以把出料较大但其他收率和较小成员作为典型成员,应该怎么给生产路线排序呢?

需要一个量来衡量生产路线的重要程度,也就是需要一个量来衡量出料的重要程度。工业上会优先关注收率较大且波动较大的出料,根据这一特点,我们把出料收率的标准差定义为该出料的重要度,即某种出料的标准差越大,该出料越重要。

收率数据X中第j种出料的重要度iptj

iptj=std(Xj)

根据上述思路,这样初始化类心C

1. 计算各出料的重要度:

iptj=std(Xj)

其中,iptj是第j种出料的重要度。

按重要度倒序排序,并记录索引Sidx

Sidx=[a_1, a_2,…, a_n],ipta_1>ipta_2>…>ipta_n

其中a_1, a_2,…, a_nn种出料按重要度倒序排序后索引。

2. 收率数据转置后按出料重要度排序XT

XT=XT(Sidx)

..

其中,XT的每一行都是一种出料的收率,重要性从上到下递减。

3. 计算每种出料收率的排名RKj,即收率越大,排名越靠后。

Rka_j=XTa_j.ranks()

其中XTa_j是第a_j种出料的收率,ranks()是排名方法。

排名矩阵RK

..

4. 找出备选类心Cb

每种出料都可能对应一条生产路线,我们不妨把所有出料的典型成员都找出来作为备选类心Cb

循环各出料收率,找出该出料排名减其他收率排名之和最大的点作为备选类心Cbt

Cbt=Xh,h=pmax(rka_ti-sum([rka_1i,rk a_2i,…,rka_(t-1)i,rka_(t+1)i,…,rkni])),i[1,2,…,m]\s,t[1,2,…,k]

其中Cbt是第a_t个备选类心,也是第t个重要出料,hX的第h行,也是RK的的第h列,pmax()是最大值索引方法,s是已经作为过类心的索引集合。

当出料很多时,可能会出现不同类别的初始类心是同一个点的情况,计算时要把已经作为类心的点去掉,即i[1,2,…,m]\s

这里解释一下,为什么用收率的排名数据而不直接用收率的数值计算?

因为不同出料的收率数值差距可能比较大,比如柴油收率可能是0.3-0.5之间,而液化气收率可能只有0.05-0.1之间。它们的加减受数值的影响太大,无法准确找出生产路线下的典型成员,而用收率的排名计算则忽略了数值本身的影响,可以更准确的找出生产路线下的典型成员。

如果分类数k大于出料数n,则遍历所有点,找到距离已有备选类心距离和最远的点,将其加入到备选类心集合中,直到找到k个备选类心。

Cbn+p=Xh,h=pmax(sum(dis(Cbt,Xi))),p[1,2,…,k-n],t[1,2,…,n+p], i[1,2,…,m]

其中pn个备选类心外的第p个。这里是一个循环的过程,每次循环的类心需要加入到原有的备选类心集合中,参与下次循环计算。

如果分类数k小于出料n,则只取重要性最高的k个备用类心最为最终的类心C

Cb’=Cb(Sidx)

C=[Cb’1, Cb’2,…, Cb’k]

其中,Cb’Cb按出料重要性倒序排序后的类心,C是取Cb’的前k个成员。

SPL例程


A

B

1

[[0.113,0.345,0.316],

[0.118,0.314,0.322],

[0.125,0.334,0.314],

[0.139,0.254,0.371],

[0.111,0.361,0.306],

[0.179,0.257,0.332]]

/X

2

=k=3


3

=transpose(A1)


4

=mstd@s(A3,2)


5

=A4.psort@z()

/Sidx

6

=A3(A5).(~.ranks())

/ RK

7

=as=to(A6.len()),av_idx=to(A1.len()),

A6.((oidx=as\#,pma=(~--msum(A6(oidx),1).~)(av_idx).pmax(),

res=av_idx(pma),av_idx.delete(pma),res))

/Cb索引

8

=A1(A7)

/Cb’

9

for k-A5.len()

=A1.pmax((v=~,A8.sum(dis(~,v))))

10


=A1(B9)

11


=A8.insert(0,[B10])

12

=if(k<A7.len(),A8.to(k),A8)

/初始化类心C

13

=k_means(A1,k,300,A12)


计算结果示例:

收率数据X

..

收率数据只是部分主要出料收率,所以收率和不为1,实际应用时也只是选择主要出料进行聚类。

聚类数k=3

排名矩阵RK

..

出料重要性IPT

IPT=[0.0257, 0.0455, 0.0233]

IPT倒序排序后的索引Sidx:

Sidx=[2,1,3]

初始化类心C

..

可以看到C1的第2种出料收率是三个类心中最大的,C2的第1种出料收率最大,C3的第3种出料收率最大,最大值的索引[2,1,3]刚好对应Sidx

kmeans聚类后的类心:

..

X各成员所属类别Xc

..