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
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
|
#include <stdio.h> // fprintf()
#include <unistd.h> // EXIT_{FAILURE,SUCCESS}
#include <stdlib.h> // exit()
#include "km.h"
#define UNUSED(a) ((void) (a))
// >> puts [[-1, -1], [-1, 1], [1, 1], [1, -1]].reduce([]) { |r, c| 5.times { r << [0.5 + 0.25 * c[0] + 0.4 * rand - 0.2, 0.5 + 0.25 * c[1] + 0.4 * rand - 0.2] }; r }.map { |row| '%1.3f, %1.3f,' % row }
static const float
DATA[] = {
0.132, 0.190,
0.313, 0.187,
0.076, 0.276,
0.443, 0.414,
0.136, 0.060,
0.344, 0.815,
0.259, 0.760,
0.211, 0.949,
0.103, 0.903,
0.173, 0.818,
0.873, 0.735,
0.783, 0.593,
0.845, 0.674,
0.808, 0.868,
0.871, 0.947,
0.917, 0.090,
0.691, 0.058,
0.840, 0.357,
0.783, 0.275,
0.807, 0.336,
};
#define die(...) do { \
fputs("FATAL: ", stderr); \
fprintf(stderr, __VA_ARGS__); \
fputs("\n", stderr); \
exit(EXIT_FAILURE); \
} while (0)
#define MAX_CLUSTERS 10
#define NUM_TESTS 10
static const km_shape_t
SHAPE = {
.num_floats = 2,
.num_ints = 0,
};
static void
on_search_row(
const km_search_row_t * const row,
void *cb_data
) {
UNUSED(cb_data);
printf("%zu,%0.5f,%zu\n",
row->num_clusters,
row->mean_distance,
row->num_empty_clusters
);
}
int main(int argc, char *argv[]) {
km_set_t set;
UNUSED(argc);
UNUSED(argv);
// init data set
if (!km_set_init(&set, &SHAPE, 20)) {
die("km_set_init() failed");
}
// push rows
if (!km_set_push_rows(&set, 20, DATA, NULL)) {
die("km_set_push_rows() failed");
}
// print headers
printf("num_clusters,mean_distance,num_empty_clusters\n");
// search for best solution
if (!km_search(&set, MAX_CLUSTERS, NUM_TESTS, on_search_row, NULL)) {
die("km_search()");
}
// finalize data set
km_set_fini(&set);
// return success
return 0;
}
|