算法原理
Matlab代碼
%根據lambda截集,模糊聚類
clear;
x = [80,10,6,2;
50,1,6,4;
90,6,4,6;
40,5,7,3;
10,1,2,4]; %樣本
row = size(x,1); %樣本個數
x2 = bz(x); %標准化
R = gm(x2); %構造模糊相似矩陣
biBao = transBiBao(R); %求傳遞閉包
[L,J] = lambdaJie(biBao); %截集
[T] = juLei(L,J,row); %聚類
H = dendrogram(T); %繪制聚類譜系圖
function [x2] = bz(x)
%最大值標准化
temp = max(x);
x2 = x./temp;
end
function [R] = gm(x2)
%最大最小法構造模糊相似矩陣
row = size(x2,1);
R = zeros(row,row);
for i = 1:row
for j = 1:row
R(i,j) = sum(jiao(x2(i,:),x2(j,:)))/sum(bing(x2(i,:),x2(j,:)));
end
end
end
function [Z] = jiao(X,Y)
%兩個矩陣交
[row,col] = size(X);
Z = zeros(row,col);
for i = 1:row
Z(i,:) = min([X(i,:);Y(i,:)]);
end
end
function [Z] = bing(X,Y)
%並
[row,col] = size(X);
Z = zeros(row,col);
for i = 1:row
Z(i,:) = max([X(i,:);Y(i,:)]);
end
end
function [Ystar] = heCheng(X,R)
%合成
rowX = size(X,1);
colR = size(R,2);
Ystar = zeros(rowX,colR);
for i = 1:rowX
for j = 1:colR
Ystar(i,j) = max(min([X(i,:);R(:,j)']));
end
end
end
function [biBao] = transBiBao(X)
%傳遞背包
Y = heCheng(X,X);
while Y ~= X
X = Y;
Y = heCheng(X,X);
end
biBao = Y;
biBao = biBao-diag(diag(biBao))+eye(size(biBao));
end
function [lambda,jieMatrix] = lambdaJie(X)
%lambda截集
lambda = unique(X);
len = length(lambda);
jieMatrix = zeros([size(X),len]);
for i = 1:len
temp = X;
temp(X<=lambda(i)) = 0;
temp(X>=lambda(i)) = 1;
jieMatrix(:,:,i) = temp;
end
end
function [Z] = juLei(L,J,geShu)
%聚類
len = size(J,3); %聚類次數
mark = [-1,-1,-1]; %暫時生成,記錄每次聚類的兩個對象及此使的lambda
for i=len:-1:1 %從獨自一類到全部一類
mat = triu(J(:,:,i)); %選擇上三角矩陣
[row,col] = find(mat==1);
temp = [row,col]; %聚類的兩個對象
panDuan = [mark;[temp,ones(size(temp,1),1)*L(i)]]; %lambda
[~,temp2] = unique(panDuan(:,1:2),'rows'); %去重
mark = panDuan(temp2,:);
end
mark = mark(2:end,:); %將第一個去掉
mark(:,3) = 1-mark(:,3); %lambda反轉
T = sortrows(mark,3); %排序
T = T(geShu+1:end,:); %將獨自一類的去掉
B = T(:,1:2); %不選擇lambda
len = size(B,1);
visited = [];
Y = 1:2; %為之后setdiff做准備
Z = []; %為dendrogram做准備
flag = geShu+1; %加上中間過程類的數目,不斷遞增
for i=1:len
temp1 = B(i,:);
[C,ia] = setdiff(temp1,visited); %沒有出現過的記錄下來
if length(C) == 2
Z = [Z;[temp1,T(i,3)]];
elseif length(C) == 1 %重復的標記為flag
temp2 = setdiff(Y,ia);
temp1(temp2)= flag;
flag=flag+1;
Z = [Z;[temp1,T(i,3)]];
end
visited = [visited,C];
end
end
運行結果
