/
VectorDoubleListQuantifier.kt
35 lines (29 loc) · 1.08 KB
/
VectorDoubleListQuantifier.kt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
package week3
import kotlin.math.abs
object VectorDoubleListQuantifier : KMeansSolver<List<Double>>(
distanceBetween = ::distanceBetween,
calculateAveragePosition = ::calculateMean,
createInitialDictionary = ::createInitialMeans
) {
fun quantify(
points: List<List<Double>>,
dictSize: Int,
threshold: Double = 0.0001
): List<List<Double>> {
val dictionary = solve(points, dictSize, threshold)
return points.map { p -> closestMean(p, dictionary) }
}
}
private fun distanceBetween(p1: List<Double>, p2: List<Double>): Double {
return (p1 zip p2).sumOf { (c1, c2) -> abs(c1 - c2) }
}
private fun calculateMean(points: List<List<Double>>): List<Double> {
return points.transpose().map { it.average() }
}
private fun createInitialMeans(points: List<List<Double>>, meansNumber: Int): List<List<Double>> {
val centroid = calculateMean(points)
return (1..meansNumber).map { it.toDouble() * 2 / meansNumber }.map { times(centroid, it) }
}
fun times(point: List<Double>, n: Double): List<Double> {
return point.map { it * n }
}