]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Fixes to the UPDATE logic in Geopoly.
authordrh <drh@noemail.net>
Wed, 29 Aug 2018 20:52:40 +0000 (20:52 +0000)
committerdrh <drh@noemail.net>
Wed, 29 Aug 2018 20:52:40 +0000 (20:52 +0000)
FossilOrigin-Name: 7c3cee0a2a5ccacff27400c38bd708f7b9b968eb013a8fa685d876dfe85e12a6

ext/rtree/geopoly.c
ext/rtree/rtree.c
ext/rtree/visual01.txt
manifest
manifest.uuid

index 70beffd7d18a38beb452aa606d1ca8fddba7861e..39629aee703caa984d2844363445e2cdfcfab36f 100644 (file)
@@ -1122,7 +1122,8 @@ static int geopolyInit(
   */
   pSql = sqlite3_str_new(db);
   sqlite3_str_appendf(pSql, "CREATE TABLE x(_shape");
-  pRtree->nAux = 1;   /* Add one for _shape */
+  pRtree->nAux = 1;         /* Add one for _shape */
+  pRtree->nAuxNotNull = 1;  /* The _shape column is always not-null */
   for(ii=3; ii<argc; ii++){
     pRtree->nAux++;
     sqlite3_str_appendf(pSql, ",%s", argv[ii]);
@@ -1396,6 +1397,7 @@ static int geopolyColumn(sqlite3_vtab_cursor *cur, sqlite3_context *ctx, int i){
 
   if( rc ) return rc;
   if( p==0 ) return SQLITE_OK;
+  if( i==0 && sqlite3_vtab_nochange(ctx) ) return SQLITE_OK;
   if( i<=pRtree->nAux ){
     if( !pCsr->bAuxValid ){
       if( pCsr->pReadAux==0 ){
@@ -1465,7 +1467,6 @@ static int geopolyUpdate(
   rtreeReference(pRtree);
   assert(nData>=1);
 
-  rc = SQLITE_ERROR;
   oldRowidValid = sqlite3_value_type(aData[0])!=SQLITE_NULL;;
   oldRowid = oldRowidValid ? sqlite3_value_int64(aData[0]) : 0;
   newRowidValid = nData>1 && sqlite3_value_type(aData[1])!=SQLITE_NULL;
@@ -1489,7 +1490,7 @@ static int geopolyUpdate(
 
     /* If a rowid value was supplied, check if it is already present in 
     ** the table. If so, the constraint has failed. */
-    if( newRowidValid ){
+    if( newRowidValid && (!oldRowidValid || oldRowid!=newRowid) ){
       int steprc;
       sqlite3_bind_int64(pRtree->pReadRowid, 1, cell.iRowid);
       steprc = sqlite3_step(pRtree->pReadRowid);
@@ -1543,8 +1544,15 @@ static int geopolyUpdate(
     int jj;
     int nChange = 0;
     sqlite3_bind_int64(pUp, 1, cell.iRowid);
-    for(jj=0; jj<pRtree->nAux; jj++){
-      if( !sqlite3_value_nochange(aData[jj+2]) ) nChange++;
+    assert( pRtree->nAux>=1 );
+    if( sqlite3_value_nochange(aData[2]) ){
+      sqlite3_bind_null(pUp, 2);
+    }else{
+      sqlite3_bind_value(pUp, 2, aData[2]);
+      nChange = 1;
+    }
+    for(jj=1; jj<pRtree->nAux; jj++){
+      nChange++;
       sqlite3_bind_value(pUp, jj+2, aData[jj+2]);
     }
     if( nChange ){
index 091c0bc6b489f48ce39b903f3e10a77f38ca0748..06efdc71f4545e7e67fa2a7353a5e22955d1f551 100644 (file)
@@ -127,6 +127,7 @@ struct Rtree {
   u8 nBytesPerCell;           /* Bytes consumed per cell */
   u8 inWrTrans;               /* True if inside write transaction */
   u8 nAux;                    /* # of auxiliary columns in %_rowid */
+  u8 nAuxNotNull;             /* Number of initial not-null aux columns */
   int iDepth;                 /* Current depth of the r-tree structure */
   char *zDb;                  /* Name of database containing r-tree table */
   char *zName;                /* Name of r-tree table */ 
@@ -3453,7 +3454,11 @@ static int rtreeSqlInit(
       sqlite3_str_appendf(p, "UPDATE \"%w\".\"%w_rowid\"SET ", zDb, zPrefix);
       for(ii=0; ii<pRtree->nAux; ii++){
         if( ii ) sqlite3_str_append(p, ",", 1);
-        sqlite3_str_appendf(p,"a%d=?%d",ii,ii+2);
+        if( ii<pRtree->nAuxNotNull ){
+          sqlite3_str_appendf(p,"a%d=coalesce(?%d,a%d)",ii,ii+2,ii);
+        }else{
+          sqlite3_str_appendf(p,"a%d=?%d",ii,ii+2);
+        }
       }
       sqlite3_str_appendf(p, " WHERE rowid=?1");
       zSql = sqlite3_str_finish(p);
index fc1b26a749a00f2f269d99ec6a000a55b0065a07..b1c808c6652b6df056847e453c83113ec24ec015 100644 (file)
@@ -536,4 +536,40 @@ SELECT geopoly_svg(poly,
        )
   FROM querypoly;
 .print '</svg>'
+
+.print '<h1>Color-Change For Overlapping Elements</h1>'
+BEGIN;
+UPDATE geo1
+   SET clr=CASE WHEN rowid IN (SELECT geo1.rowid FROM geo1, querypoly
+                                WHERE geopoly_overlap(_shape,poly))
+           THEN 'red' ELSE 'blue' END;
+.print '<svg width="1000" height="800" style="border:1px solid black">'
+SELECT geopoly_svg(_shape,
+         printf('style="fill:none;stroke:%s;stroke-width:1"',geo1.clr)
+       )
+  FROM geo1;
+SELECT geopoly_svg(poly,'style="fill:none;stroke:black;stroke-width:2"')
+  FROM querypoly;
+ROLLBACK;
+.print '</svg>'
+
+.print '<h1>Color-Change And Move Overlapping Elements</h1>'
+BEGIN;
+UPDATE geo1
+   SET clr=CASE WHEN rowid IN (SELECT geo1.rowid FROM geo1, querypoly
+                                WHERE geopoly_overlap(_shape,poly))
+           THEN 'red' ELSE 'blue' END;
+UPDATE geo1
+   SET _shape=geopoly_xform(_shape,1,0,0,1,300,0)
+ WHERE geopoly_overlap(_shape,(SELECT poly FROM querypoly));
+.print '<svg width="1000" height="800" style="border:1px solid black">'
+SELECT geopoly_svg(_shape,
+         printf('style="fill:none;stroke:%s;stroke-width:1"',geo1.clr)
+       )
+  FROM geo1;
+SELECT geopoly_svg(poly,'style="fill:none;stroke:black;stroke-width:2"')
+  FROM querypoly;
+ROLLBACK;
+.print '</svg>'
+
 .print '</html>'
index 0f6348fb6f43f2b3fcafc2a7d66b5582c39ec269..c9093d9428154c5f41a69603485908c67968e8f5 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Also\sfree\sup\sthe\sMEM_RowSet\sbit\sin\sthe\sMem.flags\sfield\sand\shave\sRowSet\sobjects\nbe\sdestroyed\susing\sMem.xDel.\s\sThis\schange\sresults\sin\sfaster\scode.
-D 2018-08-29T20:24:03.572
+C Fixes\sto\sthe\sUPDATE\slogic\sin\sGeopoly.
+D 2018-08-29T20:52:40.880
 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
 F Makefile.in d06f463c5b623a61ac27f5cb8214fca9e53a6704d34d6b8f2124e2b1b293c88f
@@ -359,8 +359,8 @@ F ext/repair/test/checkfreelist01.test 3e8aa6aeb4007680c94a8d07b41c339aa635cc782
 F ext/repair/test/checkindex01.test 6945d0ffc0c1dc993b2ce88036b26e0f5d6fcc65da70fc9df27c2647bb358b0f
 F ext/repair/test/test.tcl 686d76d888dffd021f64260abf29a55c57b2cedfa7fc69150b42b1d6119aac3c
 F ext/rtree/README 6315c0d73ebf0ec40dedb5aa0e942bc8b54e3761
-F ext/rtree/geopoly.c 0f1fda44b4515d2ab388f997593ac5030ff2023c6ae36fef3ca01b5bf7769e90
-F ext/rtree/rtree.c f3c2f1b5eea75b98d4d3dcdec2ebf2a69c036b53f2f3d196e61bf5016298255f
+F ext/rtree/geopoly.c 8ed95c3233ea38b6688cda8c07685cb6bf6e6e0b14208bad343c12c9f8252d3f
+F ext/rtree/rtree.c ce94cbb319423fd739702582dde47371aec8ad85207d517c41bdbf75a7ffd737
 F ext/rtree/rtree.h 4a690463901cb5e6127cf05eb8e642f127012fd5003830dbc974eca5802d9412
 F ext/rtree/rtree1.test 309afc04d4287542b2cd74f933296832cc681c7b014d9405cb329b62053a5349
 F ext/rtree/rtree2.test 5f25b01acd03470067a2d52783b2eb0a50bf836803d4342d20ca39e541220fe2
@@ -386,7 +386,7 @@ F ext/rtree/rtreeconnect.test 225ad3fcb483d36cbee423a25052a6bbae762c9576ae926833
 F ext/rtree/sqlite3rtree.h 9c5777af3d2921c7b4ae4954e8e5697502289d28
 F ext/rtree/tkt3363.test 142ab96eded44a3615ec79fba98c7bde7d0f96de
 F ext/rtree/viewrtree.tcl eea6224b3553599ae665b239bd827e182b466024
-F ext/rtree/visual01.txt 6f2fdbde3a163034a47f007c43c7b5d52952a99d8258d6aafc3d87879e904e4a
+F ext/rtree/visual01.txt e47922ab37af9589cd03aca33876fcc8eefef7c9a624e1960d14bdd2572e8d9e
 F ext/session/changeset.c 4ccbaa4531944c24584bf6a61ba3a39c62b6267a
 F ext/session/session1.test 4532116484f525110eb4cfff7030c59354c0cde9def4d109466b0df2b35ad5cc
 F ext/session/session2.test 284de45abae4cc1082bc52012ee81521d5ac58e0
@@ -1758,7 +1758,7 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
 F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
 F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P 62db5fd47660bbc4fcf2c6d4a6c5a3077f12c6442a128d22b66b789a0409ef32
-R b874f6bc6fe7e6d492c17f3293f43632
+P f48e9feb3fca514e4e586932e6d19a5e34a384204effeba553006dcddf5f13d2
+R c11872ace9ae24cb28c40999f97e723f
 U drh
-Z e2bd09cc55c8cf3a3298f3d931f8e0b9
+Z 581e01d30ec7f16b604718e3d6a88b37
index 688e6449a1aaff95db1a3734113464903fc1750f..b6bf5f9d2238a933e0b3ad7429318a47e96442e4 100644 (file)
@@ -1 +1 @@
-f48e9feb3fca514e4e586932e6d19a5e34a384204effeba553006dcddf5f13d2
\ No newline at end of file
+7c3cee0a2a5ccacff27400c38bd708f7b9b968eb013a8fa685d876dfe85e12a6
\ No newline at end of file