130{
131 double* distances;
132 uint32_t p1 = 0, p2 = 0;
133 uint32_t i, j;
134 uint32_t duplicate_count = 1;
135 double max_dst = -1, current_distance;
136 double dst_p1, dst_p2;
137
138
139 assert(k > 1);
140
141
142 for (i = 1; i < n; i++)
143 {
144
145 if (!objs[i]) continue;
146
147
148 if (!objs[p1] && !objs[p2])
149 {
150 p1 = i;
151 p2 = i;
152 continue;
153 }
154
155
158 if ((dst_p1 > max_dst) || (dst_p2 > max_dst))
159 {
160 if (dst_p1 > dst_p2)
161 {
162 max_dst = dst_p1;
163 p2 = i;
164 }
165 else
166 {
167 max_dst = dst_p2;
168 p1 = i;
169 }
170 }
171 if ((dst_p1 == 0) || (dst_p2 == 0)) duplicate_count++;
172 }
173 if (duplicate_count > 1)
175 "%s: there are at least %u duplicate inputs, number of output clusters may be less than you requested",
176 __func__,
177 duplicate_count);
178
179
180 assert(p1 != p2 && objs[p1] && objs[p2] && max_dst >= 0);
181
182
183 centers_raw[0] = *((
POINT2D *)objs[p1]);
184 centers[0] = &(centers_raw[0]);
185 centers_raw[1] = *((
POINT2D *)objs[p2]);
186 centers[1] = &(centers_raw[1]);
187
188 if (k > 2)
189 {
190
191 distances =
lwalloc(
sizeof(
double) * n);
192
193
194 for (j = 0; j < n; j++)
195 {
196 if (objs[j])
198 else
199 distances[j] = -1;
200 }
201 distances[p1] = -1;
202 distances[p2] = -1;
203
204
205 for (i = 2; i < k; i++)
206 {
207 uint32_t candidate_center = 0;
208 double max_distance = -DBL_MAX;
209
210
211 for (j = 0; j < n; j++)
212 {
213
214 if (distances[j] < 0) continue;
215
216
218 if (current_distance < distances[j])
219 distances[j] = current_distance;
220
221
222 if (distances[j] > max_distance)
223 {
224 candidate_center = j;
225 max_distance = distances[j];
226 }
227 }
228
229
230 assert(max_distance >= 0);
231
232
233 distances[candidate_center] = -1;
234
235
236 centers_raw[i] = *((
POINT2D *)objs[candidate_center]);
237 centers[i] = &(centers_raw[i]);
238 }
240 }
241}
void * lwalloc(size_t size)
void lwnotice(const char *fmt,...)
Write a notice out to the notice handler.
static double distance2d_sqr_pt_pt(const POINT2D *p1, const POINT2D *p2)