]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Demonstration code on a possible technique for optimizing the use of IN
authordrh <drh@noemail.net>
Wed, 30 May 2018 00:54:23 +0000 (00:54 +0000)
committerdrh <drh@noemail.net>
Wed, 30 May 2018 00:54:23 +0000 (00:54 +0000)
operator on columns to the right of multicolumn indexes.  If the OP_Noop
generated where were really a new opcode that checked to see if there existed
any entries in the index with a matching prefix, it might prevent unnecessary
iterations of the IN operator.

FossilOrigin-Name: 92f0fe155d5546fc7f4a443d0630613dabe149061966308e5420fad652278f16

manifest
manifest.uuid
src/where.c
src/whereInt.h
src/wherecode.c

index fad5a45c93a2949241eb2d96934320a317e9dcaa..2cfdac9d08438e34d56439057e9332da2c47c7d9 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Increase\sthe\snumber\sof\sdatabase\shandles\sopened\sby\stest\sscript\soserror.test\sto\nprovoke\san\s"out\sof\sfile-descriptors"\serror\sto\s20000\s(from\s2000).
-D 2018-05-29T19:12:58.327
+C Demonstration\scode\son\sa\spossible\stechnique\sfor\soptimizing\sthe\suse\sof\sIN\noperator\son\scolumns\sto\sthe\sright\sof\smulticolumn\sindexes.\s\sIf\sthe\sOP_Noop\ngenerated\swhere\swere\sreally\sa\snew\sopcode\sthat\schecked\sto\ssee\sif\sthere\sexisted\nany\sentries\sin\sthe\sindex\swith\sa\smatching\sprefix,\sit\smight\sprevent\sunnecessary\niterations\sof\sthe\sIN\soperator.
+D 2018-05-30T00:54:23.670
 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
 F Makefile.in bfc40f350586923e0419d2ea4b559c37ec10ee4b6e210e08c14401f8e340f0da
@@ -578,9 +578,9 @@ F src/vxworks.h d2988f4e5a61a4dfe82c6524dd3d6e4f2ce3cdb9
 F src/wal.c aa9cffc7a2bad6b826a86c8562dd4978398720ed41cb8ee7aa9d054eb8b456a0
 F src/wal.h 8de5d2d3de0956d6f6cb48c83a4012d5f227b8fe940f3a349a4b7e85ebcb492a
 F src/walker.c da987a20d40145c0a03c07d8fefcb2ed363becc7680d0500d9c79915591f5b1f
-F src/where.c 60ec752fcbe9f9e0271ac60548d159a540a1ee47a4f9fedc85e88a3d0e392dd1
-F src/whereInt.h cbae2bcd37cfebdb7812a8b188cdb19634ced2b9346470d1c270556b0c33ea53
-F src/wherecode.c 728c7f70731430ccdac807a79969873e1af6968bf1c4745dff3f9dd35f636cc8
+F src/where.c a9a270991e5e526151d077959b868481b28db8707bc6d29b76badd536c48225a
+F src/whereInt.h b6ab96d9c1e48d029eaaee8f9b6d05e6a2405af0ad68f684e75f21c46837ae11
+F src/wherecode.c 49256d67b95187f9b49777c0f526362f4eaaa46850700fe5020cf6b154a2fc52
 F src/whereexpr.c e90b2e76dcabc81edff56633bf281bc01d93b71e0c81482dc06925ce39f5844a
 F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2
 F test/affinity2.test a6d901b436328bd67a79b41bb0ac2663918fe3bd
@@ -1729,7 +1729,10 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
 F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
 F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P 89f56d6b0a6847b042a1556cdf79c598c9bfdbdd5f9529d508ca7b4d26a6ed38
-R d1b9772c07cea88c945a7c3a78ab0901
-U dan
-Z caf1e7dfd24b3c90db5132889b4bf8f4
+P 3b00f73456c65dfc1827fdada9afb49245f9addfa684d5ae35e69a07f39164bf
+R 150e6f6563a2a6ab67c600fc77f11cd6
+T *branch * multikey-opt-idea
+T *sym-multikey-opt-idea *
+T -sym-trunk *
+U drh
+Z 0e3a9a98888882656fe85b8d1be89ddd
index 16cd4a0a40d06de584b36153549ff2ec5d278e79..60b47eade3efd6cc332df0473052c6ee506190ac 100644 (file)
@@ -1 +1 @@
-3b00f73456c65dfc1827fdada9afb49245f9addfa684d5ae35e69a07f39164bf
\ No newline at end of file
+92f0fe155d5546fc7f4a443d0630613dabe149061966308e5420fad652278f16
\ No newline at end of file
index b83915e2646b37961cbbb61d989a488998460ff8..b93e2260e68e86afa68c43495b724871e6bde63e 100644 (file)
@@ -5083,6 +5083,10 @@ void sqlite3WhereEnd(WhereInfo *pWInfo){
       for(j=pLevel->u.in.nIn, pIn=&pLevel->u.in.aInLoop[j-1]; j>0; j--, pIn--){
         sqlite3VdbeJumpHere(v, pIn->addrInTop+1);
         if( pIn->eEndLoopOp!=OP_Noop ){
+          if( pIn->nPrefix ){
+            sqlite3VdbeAddOp3(v, OP_Noop, pLevel->iIdxCur,
+                              pIn->iBase, pIn->nPrefix);
+          }
           sqlite3VdbeAddOp2(v, pIn->eEndLoopOp, pIn->iCur, pIn->addrInTop);
           VdbeCoverage(v);
           VdbeCoverageIf(v, pIn->eEndLoopOp==OP_PrevIfOpen);
index 4b6213af31eb52a4f2a5ea6a503df90a51b1fe67..08159fe28e3f2888db5bda82e873ee401d6c6496 100644 (file)
@@ -82,6 +82,8 @@ struct WhereLevel {
       struct InLoop {
         int iCur;              /* The VDBE cursor used by this IN operator */
         int addrInTop;         /* Top of the IN loop */
+        int iBase;             /* Base register of multi-key index record */
+        int nPrefix;           /* Number of prior entires in the key */
         u8 eEndLoopOp;         /* IN Loop terminator. OP_Next or OP_Prev */
       } *aInLoop;           /* Information about each nested IN operator */
     } in;                 /* Used when pWLoop->wsFlags&WHERE_IN_ABLE */
index c9edab7b0c1ec776854c80fed47384f3dd524003..1578122479f206329c57fa3010ead7f54a61ce43 100644 (file)
@@ -592,6 +592,8 @@ static int codeEqualityTerm(
           if( i==iEq ){
             pIn->iCur = iTab;
             pIn->eEndLoopOp = bRev ? OP_PrevIfOpen : OP_NextIfOpen;
+            pIn->iBase = iReg - i;
+            pIn->nPrefix = i;
           }else{
             pIn->eEndLoopOp = OP_Noop;
           }