Miniball to Matoušek-Sharir-Welzl algorithm
d3.express
d3.express
I couldn't get it to converge and I am not sure if it's just the library I am using being buggy (numeric.js) or my cost function is just bad.
Cost:
const cost = (a, b) => {
// If a encloses b, returns 0, otherwise a positive cost
const dx = b.x - a.x;
const dy = b.y - a.y;
return Math.max(
0,
-a.r + (b.r + Math.sqrt(dx * dx + dy * dy))
);
}
let iter = 0;
const costAll = ([x, y, r]) => {
// Cost of enclosing all balls (which should be 0) plus cost of radius (which should get us the smallest ball)
const a = { x, y, r };
const radiusCost = Math.abs(a.r);
let encloseCost = 0;
for (let i = 0; i < B.length; i++) {
encloseCost += cost(a, B[i]);
}
const totalCost = encloseCost + radiusCost;
return totalCost;
}
Demo:https://codepen.io/anon/pen/ZyEaaQ?editors=0010
EDIT: demo should work correctly after mbostock's hint below!
This was the final cost function that worked:
let encloseCost = 0;
let farthestPointCost = 0;
for (let i = 0; i < B.length; i++) {
const b = B[i];
const dx = b.x - a.x;
const dy = b.y - a.y;
encloseCost += Math.max(
0,
-a.r + (b.r + Math.sqrt(dx * dx + dy * dy))
);
farthestPointCost = Math.max(
farthestPointCost,
b.r + Math.sqrt(dx * dx + dy * dy)
);
}
const radiusCost = Math.abs(a.r);
const totalCost = encloseCost + farthestPointCost + radiusCost;[0]: https://people.inf.ethz.ch/gaertner/subdir/software/miniball...
[1]: https://www.ti.inf.ethz.ch/ew/courses/ApproxGeom05/paper/fis...
The analogy would be that any three points on a plane describe both the vertices of exactly one triangle and exactly one circle circumscribing it (your statement) and that an infinite number of circumscribed triangles can be found for any nontrivial circle (my statement).