Skip to content
Permalink
Browse files
Added python version
  • Loading branch information
David committed Oct 28, 2020
1 parent 12314d5 commit 4fd9083563f59531ab601acfd6de2794e7c5069a
Show file tree
Hide file tree
Showing 4 changed files with 133 additions and 0 deletions.
BIN +1.07 KB (170%) Solutions/solutions.zip
Binary file not shown.
@@ -0,0 +1,42 @@
import math

from pyinclude.draw import *
from pyinclude.point import *

K = 3
POINTS = 100
RANGE = 640


if __name__ == "__main__":
points = [ Point() for i in range(POINTS) ]
centroids = [ Centroid() for i in range(K) ]

maxIterations = 10

# set random point positions
# generate K initial points and then position the rest of the
# points around the initial K
assert( len(points) >= len(centroids) )
for p in points[:len(centroids)]:
p.randomise( RANGE )

for i in range( len(centroids), len(points) ):
points[i].randomise( RANGE, points[i%len(centroids)] )

# set random starting positions for the centroids
for c in centroids:
c.randomise( RANGE )
print( c )

# clustering iterations
for i in range( maxIterations ):
# kmeans

# display centroid positions
print( f"Iteration {i}" )
for c in centroids:
print( c )

draw( points, centroids, RANGE, RANGE, f"{i:0{int(math.log(maxIterations,10)+1)}d}_clusters.bmp" )

@@ -0,0 +1,50 @@
from PIL import Image, ImageColor, ImageDraw

__colormap = (
(255, 0, 0), (255, 31, 0), (255, 63, 0), (255, 95, 0), (255, 127, 0),
(255, 159, 0), (255, 191, 0), (255, 223, 0), (255, 255, 0), (223, 255, 0),
(191, 255, 0), (159, 255, 0), (127, 255, 0), ( 95, 255, 0), ( 63, 255, 0),
( 31, 255, 0), ( 0, 255, 0), ( 0, 255, 31), ( 0, 255, 63), ( 0, 255, 95),
( 0, 255, 127), ( 0, 255, 159), ( 0, 255, 191), ( 0, 255, 223), ( 0, 255, 255),
( 0, 223, 255), ( 0, 191, 255), ( 0, 159, 255), ( 0, 127, 255), ( 0, 95, 255),
( 0, 63, 255), ( 0, 31, 255), ( 0, 0, 255), ( 31, 0, 255), ( 63, 0, 255),
( 95, 0, 255), (127, 0, 255), (159, 0, 255), (191, 0, 255), (223, 0, 255),
(255, 0, 255), (255, 0, 223), (255, 0, 191), (255, 0, 159), (255, 0, 127),
(255, 0, 95), (255, 0, 63), (255, 0, 31), (255, 255, 255), ( 0, 0, 0)
)

def draw( points, centroids, width=0, height=0, filename="temp.bmp" ):
_width = 0
_height = 0
clusters = 0

# find width, heigth based on max x, y of points, centroids
for p in points + centroids:
if p.cluster > clusters: clusters = p.cluster
if p.x > _width: _width = p.x
if p.y > _height: _height = p.y

clusters += 1
_width += 1
_height += 1

# use out values if user hasn't specified any dimensions
if width==0 or height==0:
width = _width
height = _height

# create the image
image = Image.new( "RGB", (width,height), (255,255,255) )
draw = ImageDraw.Draw( image )

colors = [ __colormap[i] for i in range( 0, len(__colormap), int(len(__colormap)/clusters)) ]

# draw the points
for p in points:
draw.ellipse( (p.x-2, p.y-2, p.x+2, p.y+2), fill=colors[p.cluster] )

# draw the clusters
for c in centroids:
draw.ellipse( (c.x-5, c.y-5, c.x+5, c.y+5), outline=colors[c.cluster] )

image.save( filename )
@@ -0,0 +1,41 @@
import random

class Coord:
def __init__( self, x=0, y=0 ):
self.x = int(x)
self.y = int(y)

def __eq__( self, other ):
return self.x == other.x and self.y == other.y

def randomise( self, range, coord=None ):
if coord is None:
self.x = random.randint( 0, range )
self.y = random.randint( 0, range )
return

x = random.gauss( coord.x, range/10 )
y = random.gauss( coord.y, range/10 )

if x < 0 : x = 0
if y < 0 : y = 0
if x > range : x = range
if y > range : y = range

self.x = int(x)
self.y = int(y)

class Point( Coord ):
def __init__( self, x=0, y=0, cluster=0 ):
Coord.__init__( self, x, y )
self.cluster = cluster

class Centroid( Coord ):
__counter = 0

def __init__( self, x=0, y=0 ):
self.cluster = Centroid.__counter
Centroid.__counter += 1

def __repr__( self ):
return f"Centroid[{self.cluster}] @ ({self.x},{self.y})"

0 comments on commit 4fd9083

Please sign in to comment.