import Ġkotlin . random . Random Ċ Ċ class ĠK Means ( val Ġpoints : ĠList < Point >, Ġval Ġk : ĠInt , Ġval Ġdimension : ĠInt , Ġval Ġmin Change : ĠDouble , Ġval ĠnumOf Threads : ĠInt ) Ġ{ ĊĠĠĠ Ġprivate Ġfun Ġe uk lide an Distance ( a : Point , Ġb : Point ): Double { ĊĠĠĠĠĠĠĠ Ġvar Ġsum Ġ= Ġ 0 . 0 ĊĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil Ġa . dimension ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġsum += Math . pow ( a . point [ i ]- b . point [ i ], 2 . 0 ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn ĠMath . sqrt ( sum ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠReturns Ġindex Ġof Ġclosest Ġcentroid Ġbased Ġon Ġe uk lide an Ġdistance ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġget Closest Cent roid Index ( centroid s : ĠMutable List < Point >, Ġpoint : ĠPoint ): Int { ĊĠĠĠĠĠĠĠ Ġvar Ġclosest Ġ= Ġ- 1 ĊĠĠĠĠĠĠĠ Ġvar Ġdistance Ġ= ĠDouble . MAX _ VALUE ĊĠĠĠĠĠĠĠ Ġfor (( index , Ġcentroid ) Ġin Ġcentroid s . with Index ()){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġnew Distance Ġ= Ġe uk lide an Distance ( point , centroid ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( new Distance < distance ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġdistance Ġ= Ġnew Distance ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġclosest Ġ= Ġindex ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġclosest ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠCount s Ġnew Ġcentroid Ġpoint Ġbased Ġon Ġaverage Ġfrom Ġpoints Ġcontained Ġin Ġprovided Ġcluster ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġcount New Cent roid For Cluster ( cluster : ĠMutable List < Point >): Point { ĊĠĠĠĠĠĠĠ Ġval Ġnew Cent roid Ġ= ĠPoint ( Mutable List ( dimension ){ 0 . 0 }, Ġdimension ) ĊĠĠĠĠĠĠĠ Ġfor Ġ( point Ġin Ġcluster ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil Ġdimension ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġnew Cent roid . point [ i ] Ġ+= Ġpoint . point [ i ] ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil Ġdimension ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġnew Cent roid . point [ i ] Ġ= Ġnew Cent roid . point [ i ] Ġ/ Ġcluster . size ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġnew Cent roid ĊĠĠĠ Ġ} ĊĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠParallel Ġcreates Ġnew Ġcentroid Ġfor Ġall Ġclusters ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġcreate New Cent roid s Parallel ( clusters : ĠMutable List < Mutable List < Point >> ): Mutable List < Point >{ ĊĠĠĠĠĠĠĠ Ġval Ġcentroid s Ġ= Ġmutable ListOf < Point >() ĊĠĠĠĠĠĠĠ Ġval Ġthreads Ġ= Ġmutable ListOf < Thread >() ĊĠĠĠĠĠĠĠ Ġval Ġchunk Size Ġ= Ġ( k Ġ/ ĠnumOf Threads ). toInt () ĊĠĠĠĠĠĠĠ Ġif Ġ( chunk Size Ġ== Ġ 0 ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠNo Ġneed Ġto Ġmake Ġsome Ġthreads Ġcount Ġmore Ġcentroid s ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// Ġeach Ġthread Ġwill Ġcount Ġone ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( cluster Ġin Ġclusters ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġthreads . add ( Thread Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġnew Cent roid Ġ= Ġcount New Cent roid For Cluster ( cluster ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġsynchronized ( centroid s ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s . add ( new Cent roid ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ}) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġthreads [ threads . size - 1 ]. start () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} Ġelse { ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// Some Ġthreads Ġmay Ġhave Ġto Ġcount Ġmore Ġthan Ġone Ġcentroid ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil ĠnumOf Threads ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġthreads . add ( Thread { ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġp Ġ= Ġi ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġend Ġ= Ġif Ġ( i == num Of Threads - 1 ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// make Ġsure Ġthat Ġlast Ġthread Ġcounts Ġthe Ġrest Ġof Ġcentroid s ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġk ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} else Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġchunk Size *( p + 1 ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( j Ġin Ġchunk Size * p Ġuntil Ġend ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġnew Cent roid Ġ= Ġcount New Cent roid For Cluster ( clusters [ j ]) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġsynchronized ( centroid s ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s . add ( new Cent roid ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ}) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġthreads [ i ]. start () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġfor Ġ( thread Ġin Ġthreads ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġthread . join () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġreturn Ġcentroid s ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġcreate New Cent roid s Serial ( clusters : ĠMutable List < Mutable List < Point >> ): Mutable List < Point >{ ĊĠĠĠĠĠĠĠ Ġval Ġcentroid s Ġ= Ġmutable ListOf < Point >() ĊĠĠĠĠĠĠĠ Ġfor Ġ( cluster Ġin Ġclusters ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s . add ( count New Cent roid For Cluster ( cluster )) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġcentroid s ĊĠĠĠ Ġ} ĊĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠParallel Ġassigns Ġeach Ġpoint Ġinto Ġcluster Ġbased Ġon Ġclosest Ġcentroid ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġinitialize Clusters Parallel ( points : ĠList < Point >, Ġcentroid s : ĠMutable List < Point >): ĠMutable List < Mutable List < Point >> { ĊĠĠĠĠĠĠĠ Ġval Ġclusters Res Ġ= ĠMutable List ( centroid s . size ){ Ġmutable ListOf < Point >() } ĊĠĠĠĠĠĠĠ Ġval Ġthreads Ġ= Ġmutable ListOf < Thread >() ĊĠĠĠĠĠĠĠ Ġval Ġchunk Size Ġ= Ġpoints . size / num Of Threads ĊĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil ĠnumOf Threads ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġthreads . add ( Thread Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// Create Ġpoint Ġassignment Ġholder ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġclusters Ġ= ĠMutable List ( centroid s . size ){ Ġmutable ListOf < Point >() } ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġp Ġ= Ġi ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġend Ġ= Ġif Ġ( p == num Of Threads - 1 ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġpoints . size ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġchunk Size *( p + 1 ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( j Ġin Ġchunk Size * p Ġuntil Ġend ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġcentroid Index Ġ= Ġget Closest Cent roid Index ( centroid s , Ġpoints [ j ]) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġclusters [ centroid Index ]. add ( points [ j ]) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġsynchronized ( clusters Res ){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// After Ġall Ġpoints Ġwere Ġassigned Ġsynchronous ly Ġadd Ġthem Ġto Ġnew Ġclusters Ġarray ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ(( index , Ġcluster ) Ġin Ġclusters . with Index ()){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġclusters Res [ index ]. addAll ( cluster ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ}) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġthreads [ i ]. start () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġfor Ġ( thread Ġin Ġthreads ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġthread . join () ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġclusters Res ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġinitialize Clusters Serial ( points : ĠList < Point >, centroid s : ĠMutable List < Point >): ĠMutable List < Mutable List < Point >> { ĊĠĠĠĠĠĠĠ Ġval Ġclusters Ġ= ĠMutable List ( centroid s . size ){ Ġmutable ListOf < Point >() } ĊĠĠĠĠĠĠĠ Ġfor Ġ( point Ġin Ġpoints ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġclusters [ get Closest Cent roid Index ( centroid s , point )]. add ( point ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġclusters ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠChecks Ġhow Ġmuch Ġhas Ġcentroid Ġposition Ġchanged Ġsince Ġlast Ġiteration ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġcheck Cent roid Change ( centroid s : ĠMutable List < Point >, Ġnew Cent roid s : ĠMutable List < Point >): Boolean { ĊĠĠĠĠĠĠĠ Ġvar Ġcentroid _ change Ġ= Ġ 0 . 0 ĊĠĠĠĠĠĠĠ Ġfor Ġ(( index , Ġcentroid ) Ġin Ġcentroid s . with Index ()){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid _ change Ġ+= Ġe uk lide an Distance ( centroid , Ġnew Cent roid s [ index ]) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġcentroid _ change > min Change ĊĠĠĠ Ġ} ĊĊĊĠĠĠ Ġfun Ġdo K means Parallel (): ĠMutable List < Mutable List < Point >> { ĊĠĠĠĠĠĠĠ Ġvar Ġcentroid s Ġ= Ġmutable ListOf < Point >() ĊĠĠĠĠĠĠĠ Ġ// Array Ġthat Ġensures Ġthat Ġno Ġpoint Ġbecomes Ġcentroid Ġtwice ĊĠĠĠĠĠĠĠ Ġval Ġoccured Ġ= Ġmutable ListOf < Int >() ĊĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil Ġk ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġvar Ġrand Num Ġ= ĠRandom . nextInt ( points . size ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġwhile Ġ( occ ured . contains ( rand Num )){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġrand Num Ġ= ĠRandom . nextInt ( points . size ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġoccured . add ( rand Num ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s . add ( points [ rand Num ]) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġvar Ġclusters Ġ= Ġinitialize Clusters Parallel ( points , centroid s ) ĊĠĠĠĠĠĠĠ Ġvar Ġnew Cent roid s Ġ= Ġcreate New Cent roid s Parallel ( clusters ) ĊĠĠĠĠĠĠĠ Ġwhile Ġ( check Cent roid Change ( centroid s , new Cent roid s )){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s Ġ= Ġnew Cent roid s ĊĠĠĠĠĠĠĠĠĠĠĠ Ġclusters Ġ= Ġinitialize Clusters Parallel ( points , centroid s ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġnew Cent roid s Ġ= Ġcreate New Cent roid s Parallel ( clusters ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġclusters ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun Ġdo K means Serial (): Mutable List < Mutable List < Point >> { ĊĠĠĠĠĠĠĠ Ġvar Ġcentroid s Ġ= Ġmutable ListOf < Point >() ĊĠĠĠĠĠĠĠ Ġval Ġoccured Ġ= Ġmutable ListOf < Int >() ĊĠĠĠĠĠĠĠ Ġfor Ġ( i Ġin Ġ 0 Ġuntil Ġk ){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġvar Ġrand Num Ġ= ĠRandom . nextInt ( points . size ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġwhile Ġ( occ ured . contains ( rand Num )){ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġrand Num Ġ= ĠRandom . nextInt ( points . size ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġoccured . add ( rand Num ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s . add ( points [ rand Num ]) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġvar Ġclusters Ġ= Ġinitialize Clusters Serial ( points , centroid s ) ĊĠĠĠĠĠĠĠ Ġvar Ġnew Cent roid s Ġ= Ġcreate New Cent roid s Serial ( clusters ) ĊĠĠĠĠĠĠĠ Ġwhile Ġ( check Cent roid Change ( centroid s , new Cent roid s )){ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcentroid s Ġ= Ġnew Cent roid s ĊĠĠĠĠĠĠĠĠĠĠĠ Ġclusters Ġ= Ġinitialize Clusters Serial ( points , centroid s ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġnew Cent roid s Ġ= Ġcreate New Cent roid s Serial ( clusters ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġclusters ĊĠĠĠ Ġ} Ċ }