package medusa.georgios.ClusteringAlgorithms;

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Hashtable;
public class Kmeans {
    public static final float MAXVAL = Float.MAX_VALUE;
    public static final float R = 0.999f;        // See Spaeth, p. 103
    private int distance_mode = 2;	// 1: eucileadian distance; 2: cosine similarity
StringBuffer result;
    public Hashtable GiveNodeName_Get_Cluster=new Hashtable();
    
    float Threshold = 0.0001f;

	public int k = 2;
	int rows, columns;
	float distance[][];
        ArrayList labels;
	public Kmeans(int k, float distance[][], int rows, int columns) {
		this.k = k;
		this.distance = distance;
		this.rows = rows;
		this.columns = columns;
		}
        public Kmeans(int k, float distance[][], ArrayList labels_tmp) {
		this.k = k;
                this.labels=labels_tmp;
		this.distance = distance;                
		this.rows = distance.length;
		this.columns = distance.length;
                this.distance_mode=1;
		}
	public void setDistanceMode(int mode) {
		distance_mode = mode;
		}
        
      
        
        public String perform_and_get_results()
        {
            result=new StringBuffer("----------------- Cluster: 1 -----------------\n");
            GiveNodeName_Get_Cluster.clear();
            int[] cluster_result=this.performKmeans();
            int[] id=new int[cluster_result.length];
            int i,j;
            
            for ( i = 0; i < cluster_result.length; i++) id[i]=i;
            

	              for ( i = 0; i < cluster_result.length -1; i++ )
                         for ( j = i+1; j < cluster_result.length; j++)
			if(cluster_result[i] > cluster_result[j])		
			{	
				int temp = cluster_result[i];		
				cluster_result[i] = cluster_result[j];	
				cluster_result[j] = temp;	
                                int temp2 = id[i];		
				id[i] = id[j];	
				id[j] = temp2;	
			}
	
            for ( i = 0; i < cluster_result.length; i++){
                if(i>0 && cluster_result[i]!=cluster_result[i-1])
                    result.append("\n----------------- Cluster: "+cluster_result[i]+" -----------------\n");
                result.append(labels.get(id[i])+"\n");}
            
            for ( i = 0; i < cluster_result.length; i++){
                    GiveNodeName_Get_Cluster.put(labels.get(id[i]),cluster_result[i]-1);
            }
  
            String str=result.toString();
            //Save_To_File("Kmeans_clustering"+this.k+".txt",str);
             
            return str;
        }

        public String getReport()
        {
            return result.toString();
        }
      public void Save_To_File(String filename, String information)
     { 
     try {
        BufferedWriter outp = new BufferedWriter(new FileWriter(filename));  
         outp.append(information);
        outp.close();
        } catch (IOException e) {}
     
     }  
      
	public int[] performKmeans() {
		//System.out.println("hello, start to do K-means clustering...");
		int n = rows;
		int m = columns;
		int assignment[] = new int[n];

		float temp1[] = new float[columns];
		float temp2[] = new float[columns];
		MatrixClustering centers = new MatrixClustering(k, columns, 0);
		MatrixClustering old_centers;
		for (int i = 0; i < k; i ++) {
			for (int j = 0; j < columns; j ++)
			centers.set(i, j, distance[i][j]);
		}
		MatrixClustering I = new MatrixClustering(k, k, 0);
		for (int i = 0; i < k; i ++) {
			I.set(i, i, 1);
			}
		int niters = 500;
		MatrixClustering tempDistance = new MatrixClustering(rows, k, 0);
		float ss_[] = new float[columns];
		float min_[] = new float[rows];
		int index_[] = new int[rows];
		MatrixClustering post = new MatrixClustering(rows, k, 0);
		int num_of_points[] = new int[k];
		int i;
		for (int count_ = 0; count_ < niters; count_ ++) {
    		     System.out.println("iteration "+count_);	
                      old_centers = centers.copy();
                        

			for (int ii = 0; ii < rows; ii ++) {
				for (int jj = 0; jj < k; jj ++) {
					for (int kk = 0; kk < columns; kk ++){
						temp1[kk] = distance[ii][kk];
						temp2[kk] = centers.get(jj, kk);
						}						
					tempDistance.set(ii, jj, eDistance(temp1, temp2));
					}
				}
			//tempDistance.print(10, 5);
			for (int ii = 0; ii < rows; ii ++) {
				min_[ii] = tempDistance.get(ii, 0);
				index_[ii] = 0;
				for (int jj = 1; jj < k; jj ++) {
					float temp_ = tempDistance.get(ii, jj);
					if (temp_ < min_[ii]) {
						min_[ii] = temp_;
						index_[ii] = jj;					
						}
					}
				}
			//System.out.print("min_, and index_:");
			/*
			for (i = 0; i < rows; i ++)
				System.out.print(" " + min_[i]);
			for (i = 0; i < rows; i ++)
				System.out.print(" " + index_[i]);
			*/

			for (i = 0; i < rows; i ++) {
				for (int ii = 0; ii < k; ii ++)
					post.set(i, ii, I.get(index_[i], ii));
				}
			//post.print(10, 5);
			for (i = 0; i < k; i ++) {
				int sum_ = 0;
				for (int ii = 0; ii < rows; ii ++)
					sum_ += post.get(ii, i);
				num_of_points[i] = (int)sum_;
				}
			/*
			System.out.print("\nnumber of points:");
			for (i = 0; i < k; i ++)
				System.out.print(" " + num_of_points[i]); */

			for (i = 0; i < k; i ++) {		//for each center
				if (num_of_points[i] > 0) {	//cluster the points belonging to the center
					for (int vv = 0; vv < columns; vv ++) ss_[vv] = 0.0f;
					for (int kk = 0; kk  

Ads help maintain this website.