PostGIS  2.5.0dev-r@@SVN_REVISION@@
LWPOINT* lwmpoint_median ( const LWMPOINT g,
double  tol,
uint32_t  maxiter,
char  fail_if_not_converged 
)

Definition at line 205 of file lwgeom_median.c.

References init_guess(), iterate_4d(), LW_TRUE, lwalloc(), lwerror(), lwfree(), lwgeom_has_z(), lwmpoint_extract_points_4d(), lwpoint_construct_empty(), lwpoint_make2d(), lwpoint_make3dz(), LWMPOINT::srid, POINT3D::x, POINT3D::y, and POINT3D::z.

Referenced by lwgeom_median().

206 {
207  /* m ordinate is considered weight, if defined */
208  uint32_t npoints = 0; /* we need to count this ourselves so we can exclude empties and weightless points */
209  uint32_t i;
210  int input_empty = LW_TRUE;
211  double delta = DBL_MAX;
212  POINT3D median;
213  double* distances = NULL;
214  POINT4D* points = lwmpoint_extract_points_4d(g, &npoints, &input_empty);
215 
216  /* input validation failed, error reported already */
217  if (points == NULL) return NULL;
218 
219  if (npoints == 0)
220  {
221  lwfree(points);
222  if (input_empty)
223  {
224  return lwpoint_construct_empty(g->srid, 0, 0);
225  }
226  else
227  {
228  lwerror("Median failed to find non-empty input points with positive weight.");
229  return NULL;
230  }
231  }
232 
233  median = init_guess(points, npoints);
234 
235  distances = lwalloc(npoints * sizeof(double));
236 
237  for (i = 0; i < max_iter && delta > tol; i++)
238  {
239  delta = iterate_4d(&median, points, npoints, distances);
240  }
241 
242  lwfree(distances);
243  lwfree(points);
244 
245  if (fail_if_not_converged && delta > tol)
246  {
247  lwerror("Median failed to converge within %g after %d iterations.", tol, max_iter);
248  return NULL;
249  }
250 
251  if (lwgeom_has_z((LWGEOM*) g))
252  {
253  return lwpoint_make3dz(g->srid, median.x, median.y, median.z);
254  }
255  else
256  {
257  return lwpoint_make2d(g->srid, median.x, median.y);
258  }
259 }
void lwfree(void *mem)
Definition: lwutil.c:244
double y
Definition: liblwgeom.h:339
static POINT3D init_guess(const POINT4D *points, uint32_t npoints)
LWPOINT * lwpoint_make2d(int srid, double x, double y)
Definition: lwpoint.c:163
double x
Definition: liblwgeom.h:339
static double iterate_4d(POINT3D *curr, const POINT4D *points, uint32_t npoints, double *distances)
Definition: lwgeom_median.c:43
LWPOINT * lwpoint_construct_empty(int srid, char hasz, char hasm)
Definition: lwpoint.c:151
int lwgeom_has_z(const LWGEOM *geom)
Return LW_TRUE if geometry has Z ordinates.
Definition: lwgeom.c:923
double z
Definition: liblwgeom.h:339
unsigned int uint32_t
Definition: uthash.h:78
#define LW_TRUE
Return types for functions with status returns.
Definition: liblwgeom.h:75
LWPOINT * lwpoint_make3dz(int srid, double x, double y, double z)
Definition: lwpoint.c:173
static POINT4D * lwmpoint_extract_points_4d(const LWMPOINT *g, uint32_t *npoints, int *input_empty)
void * lwalloc(size_t size)
Definition: lwutil.c:229
int32_t srid
Definition: liblwgeom.h:466
void lwerror(const char *fmt,...)
Write a notice out to the error handler.
Definition: lwutil.c:190

Here is the call graph for this function:

Here is the caller graph for this function: