当前位置: 首页 > news >正文

使用FCM进行编码解码Python实现代码

文章目录

  • 代码整体结构
  • 第 1 部分:生成二维合成数据
    • 固定随机种子
    • means中心位置
    • covs形状
    • sizes点数
    • 生成数据
    • 裁剪到[0,1]
  • 第 2 部分:初始化隶属度矩阵
    • 为什么要按列归一化?
    • 这一步的意义
  • 第 3 部分:更新聚类中心
  • 第 4 部分:计算距离(每个样本到每个中心的距离)
    • 为什么要防止除零?
  • 第 5 部分:更新隶属度矩阵
    • 为什么先算距离?
    • 关键部分
    • 怎么理解ratio?
    • 总结
  • 第 6 部分:FCM 主循环
    • 初始化
    • 开始迭代
    • 为什么看U - U_old?
  • 第 7 部分:解码 / 重构
    • 最终结果
    • 为什么这就是解码?
  • 第 8 部分:重构误差
  • 第 9 部分:画图
    • 1 原始数据
    • 2 重构数据
    • 3 聚类中心
  • 第 10 部分:主程序
    • 生成数据
    • 设置参数
    • 运行FCM
    • 重构
    • 算误差
    • 输出结果
    • 画图
  • 10 总结
  • 代码
    • 1 导包
    • 2 生成二维合成数据
    • 3 初始化隶属度矩阵
    • 4 更新聚类中心
    • 5 计算距离
    • 6 更新隶属度矩阵
    • 7 FCM主函数
    • 8 解码(解粒化)
    • 9 重构误差
    • 10 完整代码

代码整体结构

1. generate_data() # 生成二维合成数据 2. initialize_membership() # 初始化隶属度矩阵 3. update_centers() # 更新聚类中心 4. compute_distances() # 计算样本到中心的距离 5. update_membership() # 更新隶属度矩阵 6. fcm() # FCM主循环 7. reconstruct_data() # 解码/重构 8. reconstruction_error() # 计算重构误差 9. plot_result() # 画图 10. main # 主程序入口

第 1 部分:生成二维合成数据

固定随机种子

means中心位置

covs形状

sizes点数

生成数据

裁剪到[0,1]

第 2 部分:初始化隶属度矩阵

为什么要按列归一化?

这一步的意义

给每个样本随机分配一个“模糊归属”

第 3 部分:更新聚类中心



哪个点对某个簇的隶属度大,它对这个簇中心的贡献就更大。所以聚类中心不是简单平均,而是加权平均。

第 4 部分:计算距离(每个样本到每个中心的距离)


为什么要防止除零?

第 5 部分:更新隶属度矩阵

为什么先算距离?

因为 FCM 的思想就是:离哪个中心近,就更属于哪个中心。所以要先知道每个点离各中心有多远。

关键部分

怎么理解ratio?

总结

隶属度是根据相对距离算出来的。

越近 → 隶属度越大 越远 → 隶属度越小

第 6 部分:FCM 主循环

初始化

开始迭代

为什么看U - U_old?

因为 FCM 最终要收敛到一个稳定状态。
如果两次隶属度矩阵几乎没变化,说明:

中心也基本稳定了 隶属度也基本稳定了 可以停止迭代

第 7 部分:解码 / 重构


最终结果

为什么这就是解码?

因为编码时,一个点被表示成:它对各中心的隶属度向量
现在解码时,又根据:隶属度、中心位置把它还原成二维点

第 8 部分:重构误差

第 9 部分:画图

1 原始数据

plt.scatter(X[:,0],X[:,1],marker='x',s=12,alpha=0.45,label='Original data')

2 重构数据

plt.scatter(X_hat[:,0],X_hat[:,1],marker='+',s=18,alpha=0.95,label='Reconstruction data')

3 聚类中心

plt.scatter(centers[:,0],centers[:,1],marker='o',s=80,alpha=0.9,label='Centers')

第 10 部分:主程序

生成数据

X=generate_data(seed=42)

设置参数

c=8m=2.0

运行FCM

centers,U=fcm(X,c=c,m=m,max_iter=200,tol=1e-5,seed=42)

重构

X_hat=reconstruct_data(centers,U,m)

算误差

V=reconstruction_error(X,X_hat)

输出结果

print("聚类中心 centers =")print(centers)print("\n隶属度矩阵 U 的形状 =",U.shape)print("重构误差 V =",V)

画图

plot_result(X,X_hat,centers)

10 总结

这段代码首先构造了一个二维合成数据集,然后使用 FCM 算法对数据进行模糊聚类,得到聚类中心和隶属度矩阵。这里的隶属度矩阵就是数据的编码结果,因为它表示每个样本对各个原型的模糊归属。接着利用聚类中心和隶属度矩阵,通过加权平均公式对每个样本进行解码重构,得到 reconstruction data,最后通过均方误差评价原始数据与重构数据之间的差异,并可视化展示结果。

代码

1 导包

importnumpyasnpimportmatplotlib.pyplotasplt

2 生成二维合成数据

1000 个点 6 组高斯分布 做过归一化
defgenerate_data(seed=42):np.random.seed(seed)means=np.array([[0.18,0.82],[0.20,0.55],[0.30,0.62],[0.42,0.40],[0.68,0.34],[0.82,0.18]])covs=[[[0.002,-0.001],[-0.001,0.006]],[[0.003,0.000],[0.000,0.005]],[[0.004,-0.002],[-0.002,0.006]],[[0.004,0.000],[0.000,0.003]],[[0.008,-0.004],[-0.004,0.003]],[[0.002,-0.001],[-0.001,0.002]]]sizes=[170,170,160,170,180,150]# 总共1000点X_list=[]formean,cov,sizeinzip(means,covs,sizes):pts=np.random.multivariate_normal(mean,cov,size)X_list.append(pts)X=np.vstack(X_list)X=np.clip(X,0,1)# 限制在 [0,1]returnX

3 初始化隶属度矩阵

definitialize_membership(n_samples,c):U=np.random.rand(c,n_samples)U=U/np.sum(U,axis=0,keepdims=True)returnU

4 更新聚类中心

defupdate_centers(X,U,m):Um=U**m centers=(Um @ X)/np.sum(Um,axis=1,keepdims=True)returncenters

5 计算距离

defcompute_distances(X,centers):# 返回 shape = (c, N)diff=X[None,:,:]-centers[:,None,:]dist=np.linalg.norm(diff,axis=2)dist=np.fmax(dist,1e-10)# 防止除零returndist

6 更新隶属度矩阵

defupdate_membership(X,centers,m):dist=compute_distances(X,centers)# (c, N)c=centers.shape[0]n=X.shape[0]U_new=np.zeros((c,n))exponent=2.0/(m-1.0)foriinrange(c):ratio=(dist[i:i+1,:]/dist)**exponent U_new[i,:]=1.0/np.sum(ratio,axis=0)returnU_new

7 FCM主函数

deffcm(X,c=8,m=2.0,max_iter=200,tol=1e-5,seed=42):np.random.seed(seed)n_samples=X.shape[0]U=initialize_membership(n_samples,c)foriterationinrange(max_iter):U_old=U.copy()centers=update_centers(X,U,m)U=update_membership(X,centers,m)diff=np.linalg.norm(U-U_old)print(f"第{iteration+1}次迭代, 隶属度变化量 ={diff:.8f}")ifdiff<tol:print("FCM 收敛")breakcenters=update_centers(X,U,m)returncenters,U

8 解码(解粒化)

defreconstruct_data(centers,U,m):Um=U**m numerator=Um.T @ centers# (N, d)denominator=np.sum(Um,axis=0,keepdims=True).T# (N, 1)X_hat=numerator/denominatorreturnX_hat

9 重构误差

defreconstruction_error(X,X_hat):returnnp.mean(np.sum((X-X_hat)**2,axis=1))

10 完整代码

importnumpyasnpimportmatplotlib.pyplotasplt# ========== 1. 生成二维合成数据 ==========defgenerate_data(seed=42):np.random.seed(seed)means=np.array([[0.18,0.82],[0.20,0.55],[0.30,0.62],[0.42,0.40],[0.68,0.34],[0.82,0.18]])covs=[[[0.002,-0.001],[-0.001,0.006]],[[0.003,0.000],[0.000,0.005]],[[0.004,-0.002],[-0.002,0.006]],[[0.004,0.000],[0.000,0.003]],[[0.008,-0.004],[-0.004,0.003]],[[0.002,-0.001],[-0.001,0.002]]]sizes=[170,170,160,170,180,150]# 总共1000点X_list=[]formean,cov,sizeinzip(means,covs,sizes):pts=np.random.multivariate_normal(mean,cov,size)X_list.append(pts)X=np.vstack(X_list)X=np.clip(X,0,1)# 限制在 [0,1]returnX# ========== 2. 初始化隶属度矩阵 ==========definitialize_membership(n_samples,c):U=np.random.rand(c,n_samples)U=U/np.sum(U,axis=0,keepdims=True)returnU# ========== 3. 更新聚类中心 ==========defupdate_centers(X,U,m):Um=U**m centers=(Um @ X)/np.sum(Um,axis=1,keepdims=True)returncenters# ========== 4. 计算距离 ==========defcompute_distances(X,centers):# 返回 shape = (c, N)diff=X[None,:,:]-centers[:,None,:]dist=np.linalg.norm(diff,axis=2)dist=np.fmax(dist,1e-10)# 防止除零returndist# ========== 5. 更新隶属度矩阵 ==========defupdate_membership(X,centers,m):dist=compute_distances(X,centers)# (c, N)c=centers.shape[0]n=X.shape[0]U_new=np.zeros((c,n))exponent=2.0/(m-1.0)foriinrange(c):ratio=(dist[i:i+1,:]/dist)**exponent U_new[i,:]=1.0/np.sum(ratio,axis=0)returnU_new# ========== 6. FCM主函数 ==========deffcm(X,c=8,m=2.0,max_iter=200,tol=1e-5,seed=42):np.random.seed(seed)n_samples=X.shape[0]U=initialize_membership(n_samples,c)foriterationinrange(max_iter):U_old=U.copy()centers=update_centers(X,U,m)U=update_membership(X,centers,m)diff=np.linalg.norm(U-U_old)print(f"第{iteration+1}次迭代, 隶属度变化量 ={diff:.8f}")ifdiff<tol:print("FCM 收敛")breakcenters=update_centers(X,U,m)returncenters,U# ========== 7. 解码 / 重构 ==========defreconstruct_data(centers,U,m):Um=U**m numerator=Um.T @ centers# (N, d)denominator=np.sum(Um,axis=0,keepdims=True).T# (N, 1)X_hat=numerator/denominatorreturnX_hat# ========== 8. 重构误差 ==========defreconstruction_error(X,X_hat):returnnp.mean(np.sum((X-X_hat)**2,axis=1))# ========== 9. 画图 ==========defplot_result(X,X_hat,centers):plt.figure(figsize=(7,6))plt.scatter(X[:,0],X[:,1],marker='x',s=12,alpha=0.45,label='Original data')plt.scatter(X_hat[:,0],X_hat[:,1],marker='+',s=18,alpha=0.95,label='Reconstruction data')plt.scatter(centers[:,0],centers[:,1],marker='o',s=80,alpha=0.9,label='Centers')plt.xlabel(r'$x_1$')plt.ylabel(r'$x_2$')plt.xlim(0,1)plt.ylim(0,1)plt.legend()plt.title('FCM Granulation-Degranulation')plt.show()# ========== 10. 主程序 ==========if__name__=="__main__":X=generate_data(seed=42)# 论文二维图常用参数c=8m=2.0centers,U=fcm(X,c=c,m=m,max_iter=200,tol=1e-5,seed=42)X_hat=reconstruct_data(centers,U,m)V=reconstruction_error(X,X_hat)print("\n===== 结果输出 =====")print("聚类中心 centers =")print(centers)print("\n隶属度矩阵 U 的形状 =",U.shape)print("重构误差 V =",V)plot_result(X,X_hat,centers)
http://www.jsqmd.com/news/680276/

相关文章:

  • 2026年靠谱的高端户外拉链/高端拉链/高端环保拉链厂家综合对比分析 - 行业平台推荐
  • 市政交通护栏源头厂家哪家好?2026江苏铝合金护栏定制加工厂家推荐指南 - 栗子测评
  • 2026水处理设备供应源头厂家:中水回用水处理系统与纯净水设备供应源头厂家推荐 - 栗子测评
  • 普洱醒茶的两种方式:干醒与湿醒分别怎么做
  • 耐火纤维棉块铸造件退火热处理隧道窑/锂电负极材料耐火纤维棉块高温碳化隧道窑厂家哪家好?2026优质源头厂家推荐:东远领衔 - 栗子测评
  • 用STM32和RC522做个智能门禁:从硬件接线到代码调试的保姆级教程
  • SAP ABAP接口开发避坑:JSON数据里的回车换行符怎么处理才不报错?
  • 2026优质橡胶密封条厂家:三元乙丙胶条、橡胶密封条、硅胶密封条、三元乙丙密封条厂家 - 栗子测评
  • 在 HarmonyOS6 中实现 Material Design 3 导航栏
  • 2026年评价高的工地红模板批发/覆膜建筑木模板/文旅项目异形模板/异形结构木模板加工厂家对比推荐 - 行业平台推荐
  • 2026专业工业污水处理设备/废气治理设备厂家推荐:反渗透水处理设备、工业污水一体化处理及中水回用设备生产供应 - 栗子测评
  • 保姆级教程:在Windows 10上用Anaconda3和Cuda 10.1,为你的Tesla V100显卡配置PyTorch 1.8深度学习环境
  • 技术文档写作风格 - 图形
  • 数据关联性与趋势发现(使用千问)
  • 2026年靠谱的高端开尾拉链/高端拉链公司对比推荐 - 品牌宣传支持者
  • 2026年比较好的安徽单晶硅压力变送器/陶瓷电容压力变送器/安徽扩散硅压力变送器/不锈钢壳体压力变送器推荐品牌厂家 - 品牌宣传支持者
  • 告别黑窗口:用QT+STKX为你的航天仿真软件做个现代化GUI界面(实战分享)
  • FreeCAD 六角扳手建模教程
  • 避坑指南:在全志T113-S3的Buildroot系统中搞定移远EC200T/EC200A USB上网(RNDIS/ECM)与串口驱动
  • 2026年Q2仓储塑料波纹管选购指南:穿线波纹管、船舶包塑金属软管、设备线束塑料波纹管、软管快速接头、金属软管接头选择指南 - 优质品牌商家
  • 2026年质量好的进口松木建筑木方稳定供货厂家推荐 - 行业平台推荐
  • 如何用3步实现效率突破:开源智能工具重构网盘资源获取体验
  • RPC项目
  • 全自动切管机厂家哪家好?2026全自动切管机厂家/张家港全自动切管机厂家推荐:昊泰克领衔,一站式全自动切管机定制厂家合集 - 栗子测评
  • AI Agent的抗干扰能力:复杂环境下的决策稳定性设计
  • STM32F103跑LVGL?手把手教你用Keil MDK5和外部SRAM搞定移植(附DMA加速技巧)
  • 2026年靠谱的广东古建斗拱木模板/广东覆膜建筑木模板优质公司推荐 - 品牌宣传支持者
  • 2026年口碑好的气源处理不锈钢减压阀/气源处理不锈钢三联件/气源处理减压阀/宁波气源处理减压阀横向对比厂家推荐 - 品牌宣传支持者
  • 关键指标自动提取(使用千问)
  • 别再死记硬背SPI引脚了!一张图搞懂MOSI/MISO/SCLK/CS的别名和实战接线(附逻辑分析仪调试技巧)