code: def kmeans(points, k, cutoff):
      initial = random.sample(points, k)
      clusters = [[p] for p in initial]
      centroids = [calculateCentroid(c) for c in clusters]
      while True:
          lists = [[] for c in clusters]
          for p in points:
              smallest_distance = getDistance(p, centroids[0])
              index = 0
              for i in range(len(clusters[1:])):
                  distance = getDistance(p, centroids[i + 1])
                  if distance < smallest_distance:
                      smallest_distance = distance
                      index = i + 1
              lists[index].append(p)
          biggest_shift = 0.0
          for i in range(len(clusters)):
              if lists[i]:
                  new_cluster, new_centroid = (
                      lists[i],
                      calculateCentroid(lists[i]),
                  )
                  shift = getDistance(centroids[i], new_centroid)
                  clusters[i] = new_cluster
                  centroids[i] = new_centroid
                  biggest_shift = max(biggest_shift, shift)
          if biggest_shift < cutoff:
              break
      return clusters
  
imports: import math, random
  from functools import reduce
label_desc: Use image node_id 2 for calling a global function with example usage: kmeans(points, k, cutoff) and returns: clusters