MATLAB实现FCM和KFCM聚类算法
一、FCM算法实现
function [U, C, obj] = FCM(X, c, m, maxIter, eps)% 输入参数:% X: 数据矩阵 (n×d)% c: 聚类数% m: 模糊指数 (默认2)% maxIter: 最大迭代次数% eps: 收敛阈值% 输出:% U: 隶属度矩阵 (n×c)% C: 聚类中心 (c×d)% obj: 目标函数值序列[n, d] = size(X);U = rand(n, c);U = U ./ sum(U, 2); % 归一化for iter = 1:maxIter% 更新聚类中心C = (U.^m * X) ./ (sum(U.^m, 1)' * ones(1, d));% 计算距离矩阵dist = pdist2(X, C);% 更新隶属度U_new = dist.^(-2/(m-1));U_new = U_new ./ sum(U_new, 2);% 检查收敛if norm(U_new - U, 'fro') < epsbreak;endU = U_new;end% 计算目标函数obj = sum(sum((U.^m) .* pdist2(X, C).^2));
end
二、KFCM算法实现(带高斯核)
function [U, C, obj] = KFCM(X, c, m, maxIter, eps, kernelType, kernelParam)% 输入参数:% kernelType: 核函数类型 ('gauss', 'poly')% kernelParam: 核参数 (高斯核sigma/多项式核degree)% 其他参数同FCM[n, d] = size(X);U = rand(n, c);U = U ./ sum(U, 2);% 计算核矩阵K = computeKernelMatrix(X, kernelType, kernelParam);for iter = 1:maxIter% 更新聚类中心(核空间)C = (U.^m * K) ./ (sum(U.^m, 1)' * ones(1, size(K,2)));% 更新隶属度distKernel = K - 2*(U.^m * K*C') + (C * K * C');U_new = distKernel.^(-2/(m-1));U_new = U_new ./ sum(U_new, 2);% 检查收敛if norm(U_new - U, 'fro') < epsbreak;endU = U_new;end% 计算目标函数obj = sum(sum((U.^m) .* distKernel));
endfunction K = computeKernelMatrix(X, type, param)switch typecase 'gauss'sigma = param;K = exp(-pdist2(X, X).^2 / (2*sigma^2));case 'poly'degree = param;K = (X*X' + 1).^degree;otherwiseerror('Unsupported kernel type');end
end
三、对比实验与可视化
1. 数据生成与参数设置
% 生成测试数据
rng(1); % 固定随机种子
X = [mvnrnd([1,1], eye(2), 100); mvnrnd([4,4], eye(2), 100)];% 参数设置
c = 2; % 聚类数
m = 2; % 模糊指数
maxIter = 100;% 最大迭代次数
eps = 1e-5; % 收敛阈值
2. 算法执行与结果对比
% FCM实验
tic;
[U_fcm, C_fcm, obj_fcm] = FCM(X, c, m, maxIter, eps);
time_fcm = toc;% KFCM实验(高斯核)
tic;
[U_kfcm, C_kfcm, obj_kfcm] = KFCM(X, c, m, maxIter, eps, 'gauss', 1.0);
time_kfcm = toc;% 可视化
figure;
subplot(1,2,1);
gscatter(X(:,1), X(:,2), membership(U_fcm));
hold on;
plot(C_fcm(:,1), C_fcm(:,2), 'kx', 'MarkerSize', 12);
title(sprintf('FCM - 迭代次数: %d, 耗时: %.4f', sum(obj_fcm<eps), time_fcm));subplot(1,2,2);
gscatter(X(:,1), X(:,2), membership(U_kfcm));
hold on;
plot(C_kfcm(:,1), C_kfcm(:,2), 'kx', 'MarkerSize', 12);
title(sprintf('KFCM - 迭代次数: %d, 耗时: %.4f', sum(obj_kfcm<eps), time_kfcm));
参考代码 FCM+KFCM模糊C均值聚类分析算法matlab代码 www.youwenfan.com/contentcsi/65000.html
四、改进与优化
1. 初始化优化(KFCM)
% 使用K-means预初始化(提升收敛速度)
[idx, centers] = kmeans(X, c);
U = init_membership(X, centers);
2. 动态参数调整
% 自适应模糊指数(根据数据密度调整)
m = 1.5 + 0.5*log10(var(X(:,1))/var(X(:,2)));
3. 并行计算加速
% 使用parfor加速距离矩阵计算
parfor i = 1:nfor j = 1:cdist(i,j) = norm(X(i,:) - C(j,:));end
end
五、典型应用场景
1. 图像分割(医学影像)
% 加载MRI图像
img = imread('brainMRI.png');
grayImg = rgb2gray(img);
[X, map] = im2double(grayImg);% 转换为特征矩阵
feature = double(reshape(grayImg, [], 1));% 执行KFCM分割
[U, C, ~] = KFCM(feature, 3, 2, 200, 1e-5, 'gauss', 0.5);
segmented = reshape(U(:,1), size(grayImg));
imshow(label2rgb(reshape(argmax(U), size(grayImg))));
2. 工业故障检测
% 加载振动信号数据
load('vibration_data.mat');% 特征提取
features = extract_features(data);% 执行FCM聚类
[U, C, ~] = FCM(features, 2, 2, 100, 1e-5);% 异常检测
threshold = prctile(U(:,2), 95);
anomalies = find(U(:,2) > threshold);