Commit 4a52b643 authored by StefanoPetrilli's avatar StefanoPetrilli Committed by Dave Gosselin

MDEV-34138: Implements the function MBRCoveredBy

Returns 1 or 0 to indicate whether the minimum bounding rectangle of g1
is covered by the minimum bounding rectangle of g2. The tests have been
cherry-picked from the MySQL implementation of this function to grant
compatibility among the two implementations.
Co-authored-by: default avatarErlend Dahl <erlend.dahl@oracle.com>
Co-authored-by: default avatarNorvald H. Ryeng <norvald.ryeng@oracle.com>
Co-authored-by: default avatarMartin Hansson  <martin.hansson@oracle.com>
Co-authored-by: default avatarErik Froseth <erik.froseth@oracle.com>
Co-authored-by: default avatarHans H Melby <hans.h.melby@oracle.com>
Co-authored-by: default avatarJens Even Berg Blomsøy <jens.even.blomosoy@oracle.com>
Co-authored-by: default avatarDavid Zhao <david.zhao@oracle.com>
Co-authored-by: default avatarBennyWang <benny.wang@oracle.com>
parent f21ee74e
......@@ -1032,6 +1032,7 @@ static COMMANDS commands[] = {
{ "MASTER_POS_WAIT", 0, 0, 0, ""},
{ "MAX", 0, 0, 0, ""},
{ "MBRCONTAINS", 0, 0, 0, ""},
{ "MBRCOVEREDBY", 0, 0, 0, ""},
{ "MBRDISJOINT", 0, 0, 0, ""},
{ "MBREQUAL", 0, 0, 0, ""},
{ "MBRINTERSECTS", 0, 0, 0, ""},
......
This diff is collapsed.
This diff is collapsed.
......@@ -97,7 +97,7 @@ class Item_func :public Item_func_or_sum
INTERVAL_FUNC, ISNOTNULLTEST_FUNC,
SP_EQUALS_FUNC, SP_DISJOINT_FUNC,SP_INTERSECTS_FUNC,
SP_TOUCHES_FUNC,SP_CROSSES_FUNC,SP_WITHIN_FUNC,
SP_CONTAINS_FUNC,SP_OVERLAPS_FUNC,
SP_CONTAINS_FUNC, SP_COVEREDBY_FUNC, SP_OVERLAPS_FUNC,
SP_STARTPOINT,SP_ENDPOINT,SP_EXTERIORRING,
SP_POINTN,SP_GEOMETRYN,SP_INTERIORRINGN, SP_RELATE_FUNC,
NOT_FUNC, NOT_ALL_FUNC, TEMPTABLE_ROWID,
......
......@@ -1135,10 +1135,12 @@ Item_func_spatial_rel::get_mm_leaf(RANGE_OPT_PARAM *param,
LEX_CSTRING Item_func_spatial_mbr_rel::func_name_cstring() const
{
{
switch (spatial_rel) {
case SP_CONTAINS_FUNC:
return { STRING_WITH_LEN("mbrcontains") };
case SP_COVEREDBY_FUNC:
return { STRING_WITH_LEN("mbrcoveredby") };
case SP_WITHIN_FUNC:
return { STRING_WITH_LEN("mbrwithin") } ;
case SP_EQUALS_FUNC:
......@@ -1179,9 +1181,15 @@ longlong Item_func_spatial_mbr_rel::val_int()
g2->get_mbr(&mbr2, &dummy) || !mbr2.valid())))
return 0;
uint32 srid1= uint4korr(res1->ptr()), srid2= uint4korr(res2->ptr());
if (srid1 != srid2)
my_error(ER_GIS_DIFFERENT_SRIDS, MYF(0), func_name(), srid1, srid2);
switch (spatial_rel) {
case SP_CONTAINS_FUNC:
return mbr1.contains(&mbr2);
case SP_COVEREDBY_FUNC:
return mbr1.coveredby(&mbr2);
case SP_WITHIN_FUNC:
return mbr1.within(&mbr2);
case SP_EQUALS_FUNC:
......@@ -1205,11 +1213,14 @@ longlong Item_func_spatial_mbr_rel::val_int()
}
LEX_CSTRING Item_func_spatial_precise_rel::func_name_cstring() const
{
{
switch (spatial_rel) {
case SP_CONTAINS_FUNC:
return { STRING_WITH_LEN("st_contains") };
case SP_COVEREDBY_FUNC:
return { STRING_WITH_LEN("st_coveredby") };
case SP_WITHIN_FUNC:
return { STRING_WITH_LEN("st_within") };
case SP_EQUALS_FUNC:
......@@ -3080,6 +3091,38 @@ class Create_func_contains : public Create_func_arg2
};
class Create_func_mbr_coveredby : public Create_func_arg2
{
public:
Item *create_2_arg(THD *thd, Item *arg1, Item *arg2) override
{
return new (thd->mem_root) Item_func_spatial_mbr_rel(thd, arg1, arg2,
Item_func::SP_COVEREDBY_FUNC);
}
static Create_func_mbr_coveredby s_singleton;
protected:
Create_func_mbr_coveredby() = default;
~Create_func_mbr_coveredby() override = default;
};
class Create_func_coveredby : public Create_func_arg2
{
public:
Item *create_2_arg(THD *thd, Item *arg1, Item *arg2) override
{
return new (thd->mem_root) Item_func_spatial_precise_rel(thd, arg1, arg2,
Item_func::SP_COVEREDBY_FUNC);
}
static Create_func_coveredby s_singleton;
protected:
Create_func_coveredby() = default;
~Create_func_coveredby() override = default;
};
class Create_func_crosses : public Create_func_arg2
{
public:
......@@ -4087,6 +4130,7 @@ Create_func_boundary Create_func_boundary::s_singleton;
Create_func_buffer Create_func_buffer::s_singleton;
Create_func_centroid Create_func_centroid::s_singleton;
Create_func_contains Create_func_contains::s_singleton;
Create_func_coveredby Create_func_coveredby::s_singleton;
Create_func_convexhull Create_func_convexhull::s_singleton;
Create_func_crosses Create_func_crosses::s_singleton;
Create_func_difference Create_func_difference::s_singleton;
......@@ -4113,6 +4157,7 @@ Create_func_isempty Create_func_isempty::s_singleton;
Create_func_isring Create_func_isring::s_singleton;
Create_func_issimple Create_func_issimple::s_singleton;
Create_func_mbr_contains Create_func_mbr_contains::s_singleton;
Create_func_mbr_coveredby Create_func_mbr_coveredby::s_singleton;
Create_func_mbr_disjoint Create_func_mbr_disjoint::s_singleton;
Create_func_mbr_equals Create_func_mbr_equals::s_singleton;
Create_func_mbr_intersects Create_func_mbr_intersects::s_singleton;
......@@ -4154,6 +4199,7 @@ static Native_func_registry func_array_geom[] =
{ { STRING_WITH_LEN("BUFFER") }, GEOM_BUILDER(Create_func_buffer)},
{ { STRING_WITH_LEN("CENTROID") }, GEOM_BUILDER(Create_func_centroid)},
{ { STRING_WITH_LEN("CONTAINS") }, GEOM_BUILDER(Create_func_contains)},
{ { STRING_WITH_LEN("COVEREDBY") }, GEOM_BUILDER(Create_func_coveredby)},
{ { STRING_WITH_LEN("CONVEXHULL") }, GEOM_BUILDER(Create_func_convexhull)},
{ { STRING_WITH_LEN("CROSSES") }, GEOM_BUILDER(Create_func_crosses)},
{ { STRING_WITH_LEN("DIMENSION") }, GEOM_BUILDER(Create_func_dimension)},
......@@ -4184,6 +4230,7 @@ static Native_func_registry func_array_geom[] =
{ { STRING_WITH_LEN("LINESTRINGFROMTEXT") }, GEOM_BUILDER(Create_func_geometry_from_text)},
{ { STRING_WITH_LEN("LINESTRINGFROMWKB") }, GEOM_BUILDER(Create_func_geometry_from_wkb)},
{ { STRING_WITH_LEN("MBRCONTAINS") }, GEOM_BUILDER(Create_func_mbr_contains)},
{ { STRING_WITH_LEN("MBRCOVEREDBY") }, GEOM_BUILDER(Create_func_mbr_coveredby)},
{ { STRING_WITH_LEN("MBRDISJOINT") }, GEOM_BUILDER(Create_func_mbr_disjoint)},
{ { STRING_WITH_LEN("MBREQUAL") }, GEOM_BUILDER(Create_func_mbr_equals)},
{ { STRING_WITH_LEN("MBREQUALS") }, GEOM_BUILDER(Create_func_mbr_equals)},
......@@ -4228,6 +4275,7 @@ static Native_func_registry func_array_geom[] =
{ { STRING_WITH_LEN("ST_BUFFER") }, GEOM_BUILDER(Create_func_buffer)},
{ { STRING_WITH_LEN("ST_CENTROID") }, GEOM_BUILDER(Create_func_centroid)},
{ { STRING_WITH_LEN("ST_CONTAINS") }, GEOM_BUILDER(Create_func_contains)},
{ { STRING_WITH_LEN("ST_COVEREDBY") }, GEOM_BUILDER(Create_func_coveredby)},
{ { STRING_WITH_LEN("ST_CONVEXHULL") }, GEOM_BUILDER(Create_func_convexhull)},
{ { STRING_WITH_LEN("ST_CROSSES") }, GEOM_BUILDER(Create_func_crosses)},
{ { STRING_WITH_LEN("ST_DIFFERENCE") }, GEOM_BUILDER(Create_func_difference)},
......
......@@ -27,7 +27,7 @@ double my_double_round(double value, longlong dec, bool dec_unsigned,
#ifdef HAVE_SPATIAL
/*
/*
exponential notation :
1 sign
1 number before the decimal point
......@@ -142,6 +142,21 @@ int MBR::within(const MBR *mbr)
}
int MBR::coveredby(const MBR *mbr)
{
int dim1= dimension();
int dim2= mbr->dimension();
if (dim1 > dim2)
return 0;
else if (dim1 == 0 && dim2 == 0)
return equals(mbr);
return ((xmin >= mbr->xmin) && (xmax <= mbr->xmax) &&
(ymin >= mbr->ymin) && (ymax <= mbr->ymax));
}
/***************************** Gis_class_info *******************************/
Geometry::Class_info *Geometry::ci_collection[Geometry::wkb_last+1]=
......
......@@ -154,6 +154,8 @@ struct MBR
(mbr->xmax <= xmax) && (mbr->ymax <= ymax));
}
int coveredby(const MBR *mbr);
bool inner_point(double x, double y) const
{
/* The following should be safe, even if we compare doubles */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment