k_means聚类算法的实现

本文介绍了一个简单的聚类算法实现过程,适用于对象具有单一属性的数据集。通过迭代更新聚类中心来最小化准则函数,实现数据的自动分类。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

该聚类算法不描述,下面的算法是针对对象只有单一属性的集合。

运行速度有些慢。可以将准则函数的收敛判断替换成进行迭代的次数

 

#include"stdio.h"
#include"iostream"
#include"time.h"
#include"math.h"
using namespace std;
#define max 1000
typedef struct ts_uc_arr
{
 float d;//存储初始数据
 int ic;//所属的聚类
} ts_uc_arr;
void main()
{
 //cout<<"Hello"<<endl;
  float tsum = 0;
  int tcount = 0;
 int j;
 float e = 0;//准则函数
 float et = -2;//存储准则函数上次的计算值
 int n;
 int k;//要分的簇数
 int tmpk=-1;//暂存该对象是属于哪个簇的
 float dis=3.4e38;//对象计算的距离
 float *f_cen_arr;
 cout<<"Input n Objects:"<<endl;

 cin>>n;
 ts_uc_arr * tst_uc_arr = new ts_uc_arr[n];
 srand((unsigned)time(NULL));
 for(int i = 0;i < n;i++)//生成初始的待分类数据
 {
  tst_uc_arr[i].d = (float)(rand()/max);
  tst_uc_arr[i].ic = -1;
  //cout<<tst_uc_arr[i].d<<":"<<tst_uc_arr[i].ic<<endl;
 }
 cout<<"Input how many clusters to calculate:"<<endl;
 cin>>k;
 f_cen_arr = new float[k];
 for(i = 0;i < k;i++)//初始化中心
 {  f_cen_arr[i] = tst_uc_arr[i].d;
    tst_uc_arr[i].ic = i;
  //cout<<f_cen_arr[i]<<":"<<tst_uc_arr[i].d<<endl;
}
 while(e - et > 1)//判别准则函数是否收敛
 {
  for(i = 0;i < n;i++)
  {
   for( j = 0;j < k;j++)
   {
    if(sqrt((tst_uc_arr[i].d-f_cen_arr[j])*(tst_uc_arr[i].d-f_cen_arr[j])) < dis)
    {
     dis = sqrt((tst_uc_arr[i].d-f_cen_arr[j])*(tst_uc_arr[i].d-f_cen_arr[j]));
     tmpk = j;
    }
    
   }
   tst_uc_arr[i].ic = tmpk;//一次计算后该对象应该所属的簇
   dis=3.4e38;//每次距离要重新初始化
  }

 
  for(j = 0;j < k;j++)//计算簇的新的中心
  {
   for(i = 0;i < n;i++)
   {
    if(tst_uc_arr[i].ic == j){tsum += tst_uc_arr[i].d;++tcount;}
   }
   f_cen_arr[j] = (tsum / tcount);
   tsum = 0;
      tcount = 0;
  }
  et = e;
  for(j = 0;j < k;j++)//计算准则函数
  {
   for(i = 0;i < n;i++)
   {
    if(tst_uc_arr[i].ic == j){tsum += (tst_uc_arr[i].d-f_cen_arr[j])*(tst_uc_arr[i].d-f_cen_arr[j]);}
   }
 
   e += tsum;

   tsum = 0;
    
  }

  
  
 }


  for( i = 0;i < n;i++)//输出聚类后的结果
 {
  //tst_uc_arr[i].d = (float)(rand()/max);
  //tst_uc_arr[i].ic = -1;
  cout<<tst_uc_arr[i].d<<":"<<tst_uc_arr[i].ic<<endl;
  // cout<<f_cen_arr[i]<<endl;
 }

}

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值