PostGIS  3.4.0dev-r@@SVN_REVISION@@

◆ lwgeom_geohash_precision()

int lwgeom_geohash_precision ( GBOX  bbox,
GBOX bounds 
)

Definition at line 763 of file lwalgorithm.c.

764 {
765  double minx, miny, maxx, maxy;
766  double latmax, latmin, lonmax, lonmin;
767  double lonwidth, latwidth;
768  double latmaxadjust, lonmaxadjust, latminadjust, lonminadjust;
769  int precision = 0;
770 
771  /* Get the bounding box, return error if things don't work out. */
772  minx = bbox.xmin;
773  miny = bbox.ymin;
774  maxx = bbox.xmax;
775  maxy = bbox.ymax;
776 
777  if ( minx == maxx && miny == maxy )
778  {
779  /* It's a point. Doubles have 51 bits of precision.
780  ** 2 * 51 / 5 == 20 */
781  return 20;
782  }
783 
784  lonmin = -180.0;
785  latmin = -90.0;
786  lonmax = 180.0;
787  latmax = 90.0;
788 
789  /* Shrink a world bounding box until one of the edges interferes with the
790  ** bounds of our rectangle. */
791  while ( 1 )
792  {
793  lonwidth = lonmax - lonmin;
794  latwidth = latmax - latmin;
795  latmaxadjust = lonmaxadjust = latminadjust = lonminadjust = 0.0;
796 
797  if ( minx > lonmin + lonwidth / 2.0 )
798  {
799  lonminadjust = lonwidth / 2.0;
800  }
801  else if ( maxx < lonmax - lonwidth / 2.0 )
802  {
803  lonmaxadjust = -1 * lonwidth / 2.0;
804  }
805  if ( lonminadjust || lonmaxadjust )
806  {
807  lonmin += lonminadjust;
808  lonmax += lonmaxadjust;
809  /* Each adjustment cycle corresponds to 2 bits of storage in the
810  ** geohash. */
811  precision++;
812  }
813  else
814  {
815  break;
816  }
817 
818  if ( miny > latmin + latwidth / 2.0 )
819  {
820  latminadjust = latwidth / 2.0;
821  }
822  else if (maxy < latmax - latwidth / 2.0 )
823  {
824  latmaxadjust = -1 * latwidth / 2.0;
825  }
826  /* Only adjust if adjustments are legal (we haven't crossed any edges). */
827  if ( latminadjust || latmaxadjust )
828  {
829  latmin += latminadjust;
830  latmax += latmaxadjust;
831  /* Each adjustment cycle corresponds to 2 bits of storage in the
832  ** geohash. */
833  precision++;
834  }
835  else
836  {
837  break;
838  }
839  }
840 
841  /* Save the edges of our bounds, in case someone cares later. */
842  bounds->xmin = lonmin;
843  bounds->xmax = lonmax;
844  bounds->ymin = latmin;
845  bounds->ymax = latmax;
846 
847  /* Each geohash character (base32) can contain 5 bits of information.
848  ** We are returning the precision in characters, so here we divide. */
849  return precision / 5;
850 }
static uint8_t precision
Definition: cu_in_twkb.c:25
double ymax
Definition: liblwgeom.h:357
double xmax
Definition: liblwgeom.h:355
double ymin
Definition: liblwgeom.h:356
double xmin
Definition: liblwgeom.h:354

References precision, GBOX::xmax, GBOX::xmin, GBOX::ymax, and GBOX::ymin.

Referenced by lwgeom_geohash(), and test_geohash_precision().

Here is the caller graph for this function: