Changeset: 5210e47b5247 for MonetDB
URL: http://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=5210e47b5247
Modified Files:
geom/monetdb5/geom.c
geom/monetdb5/geom.mal
geom/sql/40_geom.sql
monetdb5/optimizer/opt_geospatial.c
Branch: geo
Log Message:
COntains with x y coordinates + Filter using imprints (for some reason it
always returns 0 oids)
diffs (truncated from 599 to 300 lines):
diff --git a/geom/monetdb5/geom.c b/geom/monetdb5/geom.c
--- a/geom/monetdb5/geom.c
+++ b/geom/monetdb5/geom.c
@@ -156,17 +156,20 @@ geom_export str wkbTouches(bit*, wkb**,
geom_export str wkbCrosses(bit*, wkb**, wkb**);
geom_export str wkbWithin(bit*, wkb**, wkb**);
geom_export str wkbContains(bit*, wkb**, wkb**);
-geom_export str wkbContains_bat(int* outBAT_id, int* aBAT_id, int* bBAT_id);
+geom_export str wkbContains_bat(int* outBAT_id, bat*, bat*);
geom_export str wkbContains_geom_bat(int* outBAT_id, wkb** geomWKB, int*
inBAT_id);
+geom_export str wkbPointsContains_geom_bat(bat* outBAT_id, wkb** geomWKB, bat*
xBAT_id, bat* yBAT_id, int* srid);
+geom_export str wkbFilteredPointsContains_geom_bat(bat* outBAT_id, wkb**
geomWKB, bat* xBAT_id, bat* yBAT_id, bat* OIDsBAT_id, int* srid);
geom_export str wkbContains_bat_geom(int* outBAT_id, int* inBAT_id, wkb**
geomWKB);
geom_export str wkbOverlaps(bit*, wkb**, wkb**);
geom_export str wkbRelate(bit*, wkb**, wkb**, str*);
geom_export str wkbCovers(bit *out, wkb **geomWKB_a, wkb **geomWKB_b);
geom_export str wkbCoveredBy(bit *out, wkb **geomWKB_a, wkb **geomWKB_b);
-//geom_export str wkbContainsFilter_bat(int* aBATfiltered_id, int*
bBATfiltered_id, int* aBAT_id, int* bBAT_id);
-geom_export str wkbContainsFilter_geom_bat(int* BATfiltered_id, wkb** geomWKB,
int* BAToriginal_id);
-geom_export str wkbContainsFilter_bat_geom(int* BATfiltered_id, int*
BAToriginal_id, wkb** geomWKB);
+//geom_export str wkbFilter_bat(int* aBATfiltered_id, int* bBATfiltered_id,
int* aBAT_id, int* bBAT_id);
+geom_export str wkbFilter_geom_bat(int* BATfiltered_id, wkb** geomWKB, int*
BAToriginal_id);
+geom_export str wkbFilter_bat_geom(int* BATfiltered_id, int* BAToriginal_id,
wkb** geomWKB);
+geom_export str wkbFilterWithImprints_geom_bat(bat*, wkb**, bat*, bat*);
//LocateAlong
//LocateBetween
@@ -1475,6 +1478,55 @@ str geomMakePoint2D_bat(int* outBAT_id,
return MAL_SUCCEED;
}
+//it gets two BATs with x,y coordinates and returns a new BAT with the points
+static BAT* BATMakePoint2D(BAT* xBAT, BAT* yBAT) {
+ BAT *outBAT = NULL;
+ BATiter xBAT_iter, yBAT_iter;
+ BUN i;
+
+ //check if the BATs have dense heads and are aligned
+ if (!BAThdense(xBAT) || !BAThdense(yBAT)) {
+ GDKerror("BATMakePoint2D: BATs must have dense heads");
+ return NULL;
+ }
+ if(xBAT->hseqbase != yBAT->hseqbase || BATcount(xBAT) !=
BATcount(yBAT)) {
+ GDKerror("BATMakePoint2D: BATs must be aligned");
+ return NULL;
+ }
+
+ //create a new BAT
+ if ((outBAT = BATnew(TYPE_void, ATOMindex("wkb"), BATcount(xBAT),
TRANSIENT)) == NULL) {
+ GDKerror("BATMakePoint2D: Could not create new BAT for the
output");
+ return NULL;
+ }
+
+ //set the first idx of the new BAT equal to that of the x BAT (which is
equal to the y BAT)
+ BATseqbase(outBAT, xBAT->hseqbase);
+
+ //iterator over the BATs
+ xBAT_iter = bat_iterator(xBAT);
+ yBAT_iter = bat_iterator(yBAT);
+
+ for (i = BUNfirst(xBAT); i < BATcount(xBAT); i++) {
+ str err = NULL;
+ wkb* point = NULL;
+ double *x = (double*) BUNtail(xBAT_iter, i + BUNfirst(xBAT));
+ double *y = (double*) BUNtail(yBAT_iter, i + BUNfirst(yBAT));
+
+ if ((err = geomMakePoint2D(&point, x, y)) != MAL_SUCCEED) {
+ BBPreleaseref(outBAT->batCacheid);
+ GDKerror("BATMakePoint2D: %s", err);
+ GDKfree(err);
+ return NULL;
+ }
+ BUNappend(outBAT,point,TRUE); //add the result to the outBAT
+ GDKfree(point);
+ }
+
+ return outBAT;
+
+}
+
/* creates a point using the x, y, z coordinates */
str geomMakePoint3D(wkb** out, double* x, double* y, double* z) {
GEOSGeom geosGeometry = NULL;
@@ -1934,6 +1986,50 @@ str wkbSetSRID_bat(int* outBAT_id, int*
}
+static BAT* BATSetSRID(BAT* pointsBAT, int srid) {
+ BAT *outBAT = NULL;
+ BATiter pointsBAT_iter;
+ BUN p=0, q=0;
+ wkb *pointWKB = NULL;
+
+ //check if the BAT has dense heads and are aligned
+ if (!BAThdense(pointsBAT)) {
+ GDKerror("BATSetSRID: BAT must have dense heads");
+ return NULL;
+ }
+
+ //create a new BAT
+ if ((outBAT = BATnew(TYPE_void, ATOMindex("wkb"), BATcount(pointsBAT),
TRANSIENT)) == NULL) {
+ GDKerror("BATSetSRID: Could not create new BAT for the output");
+ return NULL;
+ }
+
+ //set the first idx of the new BAT equal to that of the x BAT (which is
equal to the y BAT)
+ BATseqbase(outBAT, pointsBAT->hseqbase);
+
+ //iterator over the BATs
+ pointsBAT_iter = bat_iterator(pointsBAT);
+
+ BATloop(pointsBAT, p, q) { //iterate over all valid elements
+ str err = NULL;
+ wkb *outWKB = NULL;
+
+ pointWKB = (wkb*) BUNtail(pointsBAT_iter, p);
+ if ((err = wkbSetSRID(&outWKB, &pointWKB, &srid)) !=
MAL_SUCCEED) { //set SRID
+ BBPreleaseref(outBAT->batCacheid);
+ GDKerror("BATSetSRID: %s", err);
+ GDKfree(err);
+ return NULL;
+ }
+ BUNappend(outBAT,outWKB,TRUE); //add the point to the new BAT
+ GDKfree(outWKB);
+ outWKB = NULL;
+ }
+
+ return outBAT;
+}
+
+
/* depending on the specific function it returns the X,Y or Z coordinate of a
point */
static str wkbGetCoord(double *out, wkb **geom, int dimNum, const char *name) {
//int ret=MAL_SUCCEED;
@@ -2769,7 +2865,7 @@ str wkbContains(bit *out, wkb **geomWKB_
return MAL_SUCCEED;
}
-str wkbContains_bat(int* outBAT_id, int* aBAT_id, int* bBAT_id) {
+str wkbContains_bat(int* outBAT_id, bat *aBAT_id, bat *bBAT_id) {
BAT *outBAT = NULL, *aBAT = NULL, *bBAT = NULL;
wkb *aWKB = NULL, *bWKB = NULL; //, *aWKB_previous = NULL,
*bWKB_previous = NULL;
bit outBIT;
@@ -2836,7 +2932,6 @@ str wkbContains_bat(int* outBAT_id, int*
}
-
str wkbContains_geom_bat(int* outBAT_id, wkb** geomWKB, int* inBAT_id) {
BAT *outBAT = NULL, *inBAT = NULL;
wkb *inWKB = NULL;
@@ -2895,11 +2990,193 @@ str wkbContains_bat_geom(int* outBAT_id,
return wkbContains_geom_bat(outBAT_id, geomWKB, inBAT_id);
}
+static BAT* BATContains(wkb** geomWKB, BAT* geometriesBAT) {
+ BAT *outBAT = NULL;
+ BATiter geometriesBAT_iter;
+ BUN p=0, q=0;
+ wkb *geometryWKB = NULL;
+
+ //check if the BAT has dense heads and are aligned
+ if (!BAThdense(geometriesBAT)) {
+ GDKerror("BATContains: BAT must have dense heads");
+ return NULL;
+ }
+
+ //create a new BAT
+ if ((outBAT = BATnew(TYPE_void, ATOMindex("bit"),
BATcount(geometriesBAT), TRANSIENT)) == NULL) {
+ GDKerror("BATContains: Could not create new BAT for the
output");
+ return NULL;
+ }
+
+ //set the first idx of the new BAT equal to that of the x BAT (which is
equal to the y BAT)
+ BATseqbase(outBAT, geometriesBAT->hseqbase);
+
+ //iterator over the BATs
+ geometriesBAT_iter = bat_iterator(geometriesBAT);
+
+ BATloop(geometriesBAT, p, q) { //iterate over all valid elements
+ str err = NULL;
+ bit outBIT = 0;
+
+ geometryWKB = (wkb*) BUNtail(geometriesBAT_iter, p);
+ if ((err = wkbContains(&outBIT, geomWKB, &geometryWKB)) !=
MAL_SUCCEED) { //set SRID
+ BBPreleaseref(outBAT->batCacheid);
+ GDKerror("BATContains: %s", err);
+ GDKfree(err);
+ return NULL;
+ }
+ BUNappend(outBAT,&outBIT,TRUE); //add the point to the new BAT
+ }
+
+ return outBAT;
+
+}
+
+str wkbFilteredPointsContains_geom_bat(bat* outBAT_id, wkb** geomWKB, bat*
xBAT_id, bat* yBAT_id, bat* OIDsBAT_id, int* srid) {
+ BAT *xBAT=NULL, *yBAT=NULL, *OIDsBAT=NULL, *outBAT=NULL,
*xFilteredBAT=NULL, *yFilteredBAT=NULL;
+ BAT *pointsBAT = NULL, *pointsWithSRIDBAT=NULL;
+ str ret=MAL_SUCCEED;
+
+ //get the descriptors of the BATs
+ if ((xBAT = BATdescriptor(*xBAT_id)) == NULL) {
+ throw(MAL, "batgeom.wkbContainsFiltered",
RUNTIME_OBJECT_MISSING);
+ }
+ if ((yBAT = BATdescriptor(*yBAT_id)) == NULL) {
+ BBPreleaseref(xBAT->batCacheid);
+ throw(MAL, "batgeom.wkbContainsFiltered",
RUNTIME_OBJECT_MISSING);
+ }
+ if ((OIDsBAT = BATdescriptor(*OIDsBAT_id)) == NULL) {
+ BBPreleaseref(xBAT->batCacheid);
+ BBPreleaseref(yBAT->batCacheid);
+ throw(MAL, "batgeom.wkbContainsFiltered",
RUNTIME_OBJECT_MISSING);
+ }
+fprintf(stderr, "xBAT %d\n", (int)BATcount(xBAT));
+fprintf(stderr, "yBAT %d\n", (int)BATcount(yBAT));
+fprintf(stderr, "OIDsBAT %d\n", (int)BATcount(OIDsBAT));
+
+ //check if the BATs have dense heads and are aligned
+ if (!BAThdense(xBAT) || !BAThdense(yBAT) || !BAThdense(OIDsBAT)) {
+ ret = createException(MAL, "batgeom.wkbContainsFiltered", "BATs
must have dense heads");
+ goto clean;
+ }
+ if(xBAT->hseqbase != yBAT->hseqbase || BATcount(xBAT) !=
BATcount(yBAT)) {
+ ret=createException(MAL, "batgeom.wkbContainsFiltered", "BATs
must be aligned");
+ goto clean;
+ }
+
+ //project the x and y BATs
+ xFilteredBAT = BATproject(OIDsBAT, xBAT);
+ if(xFilteredBAT == NULL) {
+ ret=createException(MAL,"batgeom.wkbContainsFiltered","Problem
projecting xBAT");
+ goto clean;
+ }
+ yFilteredBAT = BATproject(OIDsBAT, yBAT);
+ if(xFilteredBAT == NULL) {
+ ret=createException(MAL,"batgeom.wkbContainsFiltered","Problem
projecting yBAT");
+ goto clean;
+ }
+
+ //here the BAT version of some contain function that takes the BATs of
the x y coordinates should be called
+ //create the points BAT
+ if((pointsBAT = BATMakePoint2D(xFilteredBAT, yFilteredBAT)) == NULL) {
+ ret = createException(MAL, "batgeom.wkbContainsFiltered",
"Problem creating the points from the coordinates");
+ goto clean;
+ }
+ //set the srid
+ if((pointsWithSRIDBAT = BATSetSRID(pointsBAT, *srid)) == NULL) {
+ ret = createException(MAL, "batgeom.wkbContainsFiltered",
"Problem setting srid to the points");
+ goto clean;
+ }
+ //check the contains
+ if((outBAT = BATContains(geomWKB, pointsWithSRIDBAT)) == NULL) {
+ ret = createException(MAL, "batgeom.wkbContainsFiltered",
"Problem evalauting the contains");
+ goto clean;
+ }
+
+
+ BBPkeepref(*outBAT_id = outBAT->batCacheid);
+ goto clean;
+
+clean:
+ if(xBAT)
+ BBPreleaseref(xBAT->batCacheid);
+ if(yBAT)
+ BBPreleaseref(yBAT->batCacheid);
+ if(OIDsBAT)
+ BBPreleaseref(OIDsBAT->batCacheid);
+ if(xFilteredBAT)
+ BBPreleaseref(xFilteredBAT->batCacheid);
+ if(yFilteredBAT)
+ BBPreleaseref(yFilteredBAT->batCacheid);
+ if(pointsBAT)
+ BBPreleaseref(pointsBAT->batCacheid);
+ if(pointsWithSRIDBAT)
+ BBPreleaseref(pointsWithSRIDBAT->batCacheid);
+ return ret;
+}
+
+str wkbPointsContains_geom_bat(bat* outBAT_id, wkb** geomWKB, bat* xBAT_id,
bat* yBAT_id, int* srid) {
+ BAT *xBAT=NULL, *yBAT=NULL, *outBAT=NULL;
+ BAT *pointsBAT = NULL, *pointsWithSRIDBAT=NULL;
+ str ret=MAL_SUCCEED;
+
+ //get the descriptors of the BATs
+ if ((xBAT = BATdescriptor(*xBAT_id)) == NULL) {
+ throw(MAL, "batgeom.wkbContainsFiltered",
RUNTIME_OBJECT_MISSING);
+ }
+ if ((yBAT = BATdescriptor(*yBAT_id)) == NULL) {
+ BBPreleaseref(xBAT->batCacheid);
+ throw(MAL, "batgeom.wkbContainsFiltered",
RUNTIME_OBJECT_MISSING);
+ }
+
+ //check if the BATs have dense heads and are aligned
+ if (!BAThdense(xBAT) || !BAThdense(yBAT)) {
+ ret = createException(MAL, "batgeom.wkbContainsFiltered", "BATs
must have dense heads");
+ goto clean;
+ }
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list