PSO算法确定k-means初始聚类中心
2014-11-05 15:48
169 查看
import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.lang.reflect.Array;
import java.util.*;
public class Particle
{
public static void main(String[] args) throws IOException
{
PSO pso = new PSO();
pso.readfile();
pso.createpso();
pso.Initialize();
pso.Search();
}
}
class Agent
{
//result中每一行,又是一个list数组
public static List<ArrayList<Double>> result = new ArrayList<ArrayList<Double>>();
//从文件中读取数据集
public void readAgent() throws IOException
{
File file=new File("E://cluster.txt");
BufferedReader br=new BufferedReader(new FileReader(file));
String s=null;
while ((s=br.readLine())!=null)
{
String record = s.toString();
String[] fields = record.split(" ");
List<Double> tmplist = new ArrayList<Double>();
//由于第一个是K1编号,所以不录入
for (int i = 1; i < fields.length; ++i)
{
tmplist.add(Double.parseDouble(fields[i]));
}
result.add((ArrayList<Double>) tmplist);
}
br.close();
}
//对粒子的位置和速度进行初始化
public void agentinitialize()
{
//产生俩个不同的随机数,范围在[0,size-1]
Set<Integer> set = new HashSet<Integer>();
//以系统时间为种子
Random ran = new Random();
//存放结果的数组
int[] results = new int[ikmeans];
for (int i = 0; i < ikmeans; i++)
{
//产生一个范围小于result.size()的数。
int temp = ran.nextInt(result.size());
//若此数已存在,则添加失败
boolean flag=set.add(temp);
if (flag)
{
results[i] = temp;
}else
{
--i;//这次不算,重头来过
}
}
int k=0;
for(int i = 0; i < results.length; i++)
{
for (int j = 0; j < result.get(results[i]).size(); j++)
{
dpos[k]=result.get(results[i]).get(j);
dv[k] = dpbest[k] = dpos[k];
k++;
}
}
}
public void UpdateFitness()
{
//此处,如果不清楚有几个聚类中心的话,就比较难做,所以还是回归到俩个聚类中心
//俩个数组分别存放俩个聚类中心
double [] k1=new double[iAgentDim];
double [] k2=new double[iAgentDim];
//k1,k2分别所属的簇的适应度值
double m_dFitnessk1=0;
double m_dFitnessk2=0;
for (int i = 0; i < k1.length; i++)
{
k1[i]=dpos[i];
}
for (int i = 0; i < k2.length; i++)
{
k1[i]=dpos[i+k1.length];
}
//计算适应度函数的值
for (int i = 0; i <result.size(); i++)
{
double disk1=0; //一个点分别到k1,k2的距离,没有开根号
double disk2=0;
for (int j = 0; j < result.get(i).size(); j++)
{
disk1+=Math.pow(result.get(i).get(j)-k1[j], 2) ;
disk2+=Math.pow(result.get(i).get(j)-k2[j], 2) ;
//这个点距离k1比较近,是属于k1
if(disk1<=disk2)
{
m_dFitnessk1+=disk1;
}
// 这个点距离k2比较近,是属于k2
else
{
m_dFitnessk2+=disk2;
}
}
}
m_dFitness =m_dFitnessk1+m_dFitnessk2; //该粒子的总适应度
if(m_dFitness < m_dBestfitness)
{
m_dBestfitness = m_dFitness;
for(int i = 0; i < iAgentDim*ikmeans; i++)
{
dpbest[i] = dpos[i];
}
}
System.out.println(m_dBestfitness);
}
//更新粒子的速度和位置
public void UpdatePos()
{
for(int i = 0;i < iAgentDim*ikmeans;i++)
{
dv[i] = w * dv[i] + c1 * random.nextDouble() * (dpbest[i] - dpos[i]) + c2 * random.nextDouble() * ( gbest[i] - dpos[i]);
dpos[i] = dpos[i] + dv[i];
}
}
public static int iPOSNum = 20; //粒子个数
public static int iAgentDim = 2; //粒子维度
public static int ikmeans=2; //聚类中心数
private final double w = 0.9;
private final double c1= 1;
private final double c2 = 1;
public double[] dpos = new double[iAgentDim*ikmeans]; //粒子的位置
public double[] dpbest = new double[iAgentDim*ikmeans]; //粒子本身的最优位置
public double[] dv = new double[iAgentDim*ikmeans]; //粒子的速度
private double m_dFitness=0;
public double m_dBestfitness; //m_dBestfitness 粒子本身的最优解,适应度
private Random random = new Random();
public static double[] gbest = new double[iAgentDim*ikmeans];
}
class PSO
{
//构造函数,调用readAgent函数,将数据集读入
public PSO()
{
}
public void readfile() throws IOException
{
Agent fristagent=new Agent();
fristagent.readAgent();
}
//创建粒子
public void createpso()
{
m_dBestFitness = 10000;
agent = new Agent[Agent.iPOSNum];
//创建iPosnum个粒子数组
for(int i =0;i < Agent.iPOSNum;i++)
{ agent[i] = new Agent();
agent[i].agentinitialize();
}
}
public void Initialize()
{
for(int i = 0;i < Agent.iPOSNum;i++)
{
agent[i].m_dBestfitness = 10000; //将每个粒子的适应度初始为10000
agent[i].UpdateFitness();
}
}
public void Search()
{
int k = 0;
while(k < iStep) //1000
{
m_iTempPos = 99; //记录粒子全局最优值对应的下标
//对所有粒子的局部极值进行比较,更新全局极值
for(int i =0; i< Agent.iPOSNum;i++)
{
if(agent[i].m_dBestfitness < m_dBestFitness)
{
m_dBestFitness = agent[i].m_dBestfitness;
m_iTempPos = i;
}
}
//如果找到了全局极值,则更新全局极值,通过前面找到的下标
if(m_iTempPos != 99)
{
for(int i =0;i < Agent.iAgentDim*Agent.ikmeans;i++)
{
Agent.gbest[i] = agent[m_iT
9198
empPos].dpbest[i];
}
}
//更新所有粒子的位置和方向
for(int i = 0; i < Agent.iPOSNum;i++)
{
agent[i].UpdateFitness();
agent[i].UpdatePos();
}
k++;
}
//循环结束
System.out.println("After " + k + " steps " + "the best value is " + m_dBestFitness );
System.out.print("The best position is :");
for(int i = 0;i < Agent.iAgentDim*Agent.ikmeans;i++)
{
System.out.print(Agent.gbest[i] + " ");
}
}
private Agent[] agent;
private final int iStep = 10; //迭代次数
private double m_dBestFitness; //每个粒子的个体极值
private int m_iTempPos; //记录粒子全局最优值对应的下标
}
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.lang.reflect.Array;
import java.util.*;
public class Particle
{
public static void main(String[] args) throws IOException
{
PSO pso = new PSO();
pso.readfile();
pso.createpso();
pso.Initialize();
pso.Search();
}
}
class Agent
{
//result中每一行,又是一个list数组
public static List<ArrayList<Double>> result = new ArrayList<ArrayList<Double>>();
//从文件中读取数据集
public void readAgent() throws IOException
{
File file=new File("E://cluster.txt");
BufferedReader br=new BufferedReader(new FileReader(file));
String s=null;
while ((s=br.readLine())!=null)
{
String record = s.toString();
String[] fields = record.split(" ");
List<Double> tmplist = new ArrayList<Double>();
//由于第一个是K1编号,所以不录入
for (int i = 1; i < fields.length; ++i)
{
tmplist.add(Double.parseDouble(fields[i]));
}
result.add((ArrayList<Double>) tmplist);
}
br.close();
}
//对粒子的位置和速度进行初始化
public void agentinitialize()
{
//产生俩个不同的随机数,范围在[0,size-1]
Set<Integer> set = new HashSet<Integer>();
//以系统时间为种子
Random ran = new Random();
//存放结果的数组
int[] results = new int[ikmeans];
for (int i = 0; i < ikmeans; i++)
{
//产生一个范围小于result.size()的数。
int temp = ran.nextInt(result.size());
//若此数已存在,则添加失败
boolean flag=set.add(temp);
if (flag)
{
results[i] = temp;
}else
{
--i;//这次不算,重头来过
}
}
int k=0;
for(int i = 0; i < results.length; i++)
{
for (int j = 0; j < result.get(results[i]).size(); j++)
{
dpos[k]=result.get(results[i]).get(j);
dv[k] = dpbest[k] = dpos[k];
k++;
}
}
}
public void UpdateFitness()
{
//此处,如果不清楚有几个聚类中心的话,就比较难做,所以还是回归到俩个聚类中心
//俩个数组分别存放俩个聚类中心
double [] k1=new double[iAgentDim];
double [] k2=new double[iAgentDim];
//k1,k2分别所属的簇的适应度值
double m_dFitnessk1=0;
double m_dFitnessk2=0;
for (int i = 0; i < k1.length; i++)
{
k1[i]=dpos[i];
}
for (int i = 0; i < k2.length; i++)
{
k1[i]=dpos[i+k1.length];
}
//计算适应度函数的值
for (int i = 0; i <result.size(); i++)
{
double disk1=0; //一个点分别到k1,k2的距离,没有开根号
double disk2=0;
for (int j = 0; j < result.get(i).size(); j++)
{
disk1+=Math.pow(result.get(i).get(j)-k1[j], 2) ;
disk2+=Math.pow(result.get(i).get(j)-k2[j], 2) ;
//这个点距离k1比较近,是属于k1
if(disk1<=disk2)
{
m_dFitnessk1+=disk1;
}
// 这个点距离k2比较近,是属于k2
else
{
m_dFitnessk2+=disk2;
}
}
}
m_dFitness =m_dFitnessk1+m_dFitnessk2; //该粒子的总适应度
if(m_dFitness < m_dBestfitness)
{
m_dBestfitness = m_dFitness;
for(int i = 0; i < iAgentDim*ikmeans; i++)
{
dpbest[i] = dpos[i];
}
}
System.out.println(m_dBestfitness);
}
//更新粒子的速度和位置
public void UpdatePos()
{
for(int i = 0;i < iAgentDim*ikmeans;i++)
{
dv[i] = w * dv[i] + c1 * random.nextDouble() * (dpbest[i] - dpos[i]) + c2 * random.nextDouble() * ( gbest[i] - dpos[i]);
dpos[i] = dpos[i] + dv[i];
}
}
public static int iPOSNum = 20; //粒子个数
public static int iAgentDim = 2; //粒子维度
public static int ikmeans=2; //聚类中心数
private final double w = 0.9;
private final double c1= 1;
private final double c2 = 1;
public double[] dpos = new double[iAgentDim*ikmeans]; //粒子的位置
public double[] dpbest = new double[iAgentDim*ikmeans]; //粒子本身的最优位置
public double[] dv = new double[iAgentDim*ikmeans]; //粒子的速度
private double m_dFitness=0;
public double m_dBestfitness; //m_dBestfitness 粒子本身的最优解,适应度
private Random random = new Random();
public static double[] gbest = new double[iAgentDim*ikmeans];
}
class PSO
{
//构造函数,调用readAgent函数,将数据集读入
public PSO()
{
}
public void readfile() throws IOException
{
Agent fristagent=new Agent();
fristagent.readAgent();
}
//创建粒子
public void createpso()
{
m_dBestFitness = 10000;
agent = new Agent[Agent.iPOSNum];
//创建iPosnum个粒子数组
for(int i =0;i < Agent.iPOSNum;i++)
{ agent[i] = new Agent();
agent[i].agentinitialize();
}
}
public void Initialize()
{
for(int i = 0;i < Agent.iPOSNum;i++)
{
agent[i].m_dBestfitness = 10000; //将每个粒子的适应度初始为10000
agent[i].UpdateFitness();
}
}
public void Search()
{
int k = 0;
while(k < iStep) //1000
{
m_iTempPos = 99; //记录粒子全局最优值对应的下标
//对所有粒子的局部极值进行比较,更新全局极值
for(int i =0; i< Agent.iPOSNum;i++)
{
if(agent[i].m_dBestfitness < m_dBestFitness)
{
m_dBestFitness = agent[i].m_dBestfitness;
m_iTempPos = i;
}
}
//如果找到了全局极值,则更新全局极值,通过前面找到的下标
if(m_iTempPos != 99)
{
for(int i =0;i < Agent.iAgentDim*Agent.ikmeans;i++)
{
Agent.gbest[i] = agent[m_iT
9198
empPos].dpbest[i];
}
}
//更新所有粒子的位置和方向
for(int i = 0; i < Agent.iPOSNum;i++)
{
agent[i].UpdateFitness();
agent[i].UpdatePos();
}
k++;
}
//循环结束
System.out.println("After " + k + " steps " + "the best value is " + m_dBestFitness );
System.out.print("The best position is :");
for(int i = 0;i < Agent.iAgentDim*Agent.ikmeans;i++)
{
System.out.print(Agent.gbest[i] + " ");
}
}
private Agent[] agent;
private final int iStep = 10; //迭代次数
private double m_dBestFitness; //每个粒子的个体极值
private int m_iTempPos; //记录粒子全局最优值对应的下标
}
相关文章推荐
- 不共线三点确定圆心的简便算法
- user-cf算法思考-K值的确定
- html中字符编码的确定算法(一)
- 确定链表环的长度与入口,以及算法的正确性分析
- 算法学习笔记----确定n个元素的任何排列中逆序对的数目
- PSO算法学习心得
- 根据顺序三点,确定是否是顺时针的算法
- 图表轴刻度的思路,算法: 转载3【求算法:图表控件,如何确定坐标轴的范围和刻度?】
- 一种快速确定物体边缘的算法(MIT-2011-CVPR)
- 【面试经典题之字符串】实现一个算法,确定一个字符串的所有字符是否全都不同。假设不允许使用额外的数据结构
- 今日头条面试算法题——确定ABCDE五个学校名次
- 【Java,面试】实现一个算法,确定一个字符串的所有字符是否全都不同
- 算法:根据一个开关确定一百人是否都进入过房间
- 蓝桥杯 ALGO-78 算法训练 确定元音字母位置
- html中字符编码的确定算法(二)
- 确定一个字符串的所有字符全都不同算法实现
- 空间FFT确定目标位置算法matlab仿真
- pso-svm 算法实现(1):python DEAP
- 算法:对于小于1000的随机正整数,通过实验确定期望产生多少个数才能出现重复
- 带交叉因子的改进PSO算法