]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Optimize the degenerate case of a FROM clause table name enclosed all by
authordrh <drh@noemail.net>
Tue, 18 Dec 2012 19:36:11 +0000 (19:36 +0000)
committerdrh <drh@noemail.net>
Tue, 18 Dec 2012 19:36:11 +0000 (19:36 +0000)
itself inside parentheses.  Generate code as if the parentheses did not
exist, rather than the old behavior of manifesting the parenthesized table
into a transient table.  Also, tag every FROM-clause SELECT subquery that is
generated by a parenthesized FROM-clause expression using the SF_NestedFrom
flag.  The new SF_NestedFrom flag is not yet used for anything.

FossilOrigin-Name: 7fecced466d86a66b0b751c5b5608141e134fe2d

manifest
manifest.uuid
src/parse.y
src/select.c
src/sqliteInt.h
test/where8.test
test/where9.test

index 49f083d71faa852804699e2941daa232f4ca6235..9c799f1bef6e59a8cf87bdd8d6cb931c3f81c5f7 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Resolve\snames\sin\sFROM-clause\ssubqueries\sprior\sto\sresolving\snames\sin\sthe\nresult\sset\sexpressions\sof\sa\sSELECT\sstatement.
-D 2012-12-18T16:07:08.090
+C Optimize\sthe\sdegenerate\scase\sof\sa\sFROM\sclause\stable\sname\senclosed\sall\sby\nitself\sinside\sparentheses.\s\sGenerate\scode\sas\sif\sthe\sparentheses\sdid\snot\nexist,\srather\sthan\sthe\sold\sbehavior\sof\smanifesting\sthe\sparenthesized\stable\ninto\sa\stransient\stable.\s\sAlso,\stag\severy\sFROM-clause\sSELECT\ssubquery\sthat\sis\ngenerated\sby\sa\sparenthesized\sFROM-clause\sexpression\susing\sthe\sSF_NestedFrom\nflag.\s\sThe\snew\sSF_NestedFrom\sflag\sis\snot\syet\sused\sfor\sanything.
+D 2012-12-18T19:36:11.944
 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
 F Makefile.in 690d441a758cbffd13e814dc2724a721a6ebd400
 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
@@ -164,7 +164,7 @@ F src/os_unix.c ad459bb62eb6f3f6aae26d97b1a28fbac7bf0260
 F src/os_win.c ce1f5db8a7bb4d6f2092b1b2cb9631bec54a6320
 F src/pager.c 4092c907222cfd451c74fe6bd2fd64b342f7190f
 F src/pager.h 1109a06578ec5574dc2c74cf8d9f69daf36fe3e0
-F src/parse.y 15fdc2c98cbde920c2f6a0fcfd31ace646c45947
+F src/parse.y 5d5e12772845805fdfeb889163516b84fbb9ae95
 F src/pcache.c f8043b433a57aba85384a531e3937a804432a346
 F src/pcache.h 1b5dcc3dc8103d03e625b177023ee67764fa6b7c
 F src/pcache1.c 9fd22671c270b35131ef480bbc00392b8b5f8ab9
@@ -174,12 +174,12 @@ F src/printf.c 4a9f882f1c1787a8b494a2987765acf9d97ac21f
 F src/random.c cd4a67b3953b88019f8cd4ccd81394a8ddfaba50
 F src/resolve.c 52331299f4095397d6d00715b70cd153baa11931
 F src/rowset.c 64655f1a627c9c212d9ab497899e7424a34222e0
-F src/select.c f6c73171209b4af4d6b4258b6740415790415e2e
+F src/select.c 5eab6941c0ac97355817f846b77cd20bfdf5a82e
 F src/shell.c e392dd1ccbb77cc1d75a8367a89b473c24bea019
 F src/sqlite.h.in 39cc33bb08897c748fe3383c29ccf56585704177
 F src/sqlite3.rc fea433eb0a59f4c9393c8e6d76a6e2596b1fe0c0
 F src/sqlite3ext.h 6904f4aadf976f95241311fbffb00823075d9477
-F src/sqliteInt.h d1f0866c69d94fe018a32f78c31a043e3fc0d0de
+F src/sqliteInt.h f7581eb79d822a6993d6aa31baf1e67e6ff17d19
 F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d
 F src/status.c bedc37ec1a6bb9399944024d63f4c769971955a9
 F src/table.c 2cd62736f845d82200acfa1287e33feb3c15d62e
@@ -969,9 +969,9 @@ F test/where4.test e9b9e2f2f98f00379e6031db6a6fca29bae782a2
 F test/where5.test fdf66f96d29a064b63eb543e28da4dfdccd81ad2
 F test/where6.test 5da5a98cec820d488e82708301b96cb8c18a258b
 F test/where7.test 5c566388f0cc318b0032ce860f4ac5548e3c265a
-F test/where8.test a6c740fd286d7883e274e17b6230a9d672a7ab1f
+F test/where8.test 02619a9bfc6df7b19979a02852bac09c3c99477a
 F test/where8m.test da346596e19d54f0aba35ebade032a7c47d79739
-F test/where9.test bcab47eff78f1412a6aec1d6b8a3939d4a9db098
+F test/where9.test 0157862ccf0cfdf1a4622cdf697e5e2f09a8de44
 F test/whereA.test 24c234263c8fe358f079d5e57d884fb569d2da0a
 F test/whereB.test 0def95db3bdec220a731c7e4bec5930327c1d8c5
 F test/whereC.test 13ff5ec0dba407c0e0c075980c75b3275a6774e5
@@ -1026,7 +1026,7 @@ F tool/vdbe-compress.tcl f12c884766bd14277f4fcedcae07078011717381
 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
 F tool/warnings.sh fbc018d67fd7395f440c28f33ef0f94420226381
 F tool/win/sqlite.vsix 97894c2790eda7b5bce3cc79cb2a8ec2fde9b3ac
-P 7e30c021abe5a559918efaa5fc0b21db8ca782ad
-R cf6ce0613e2ebca30b9d8e27d1083ff8
+P 9b67c633d932f3e566f521ee6a9cf3be193436fa
+R d9a19320be87db9daf2926b8e71a7df8
 U drh
-Z 59025edc3e6d7e0bdfe9bc1ec0c29fc3
+Z bc761a01222fad0c80ad013442fb2ec8
index d887428c90afafe4c727296b79168e0b80047209..f26e1b6ae977523269cc213b518a6372569053f2 100644 (file)
@@ -1 +1 @@
-9b67c633d932f3e566f521ee6a9cf3be193436fa
\ No newline at end of file
+7fecced466d86a66b0b751c5b5608141e134fe2d
\ No newline at end of file
index 1d95007f04d56252d9bd4035addc8be023657140..abc0e7dc080b9c1782657b92d8ea1812a14422ab 100644 (file)
@@ -435,8 +435,8 @@ oneselect(A) ::= SELECT distinct(D) selcollist(W) from(X) where_opt(Y)
 // The "distinct" nonterminal is true (1) if the DISTINCT keyword is
 // present and false (0) if it is not.
 //
-%type distinct {int}
-distinct(A) ::= DISTINCT.   {A = 1;}
+%type distinct {u16}
+distinct(A) ::= DISTINCT.   {A = SF_Distinct;}
 distinct(A) ::= ALL.        {A = 0;}
 distinct(A) ::= .           {A = 0;}
 
@@ -513,10 +513,20 @@ seltablist(A) ::= stl_prefix(X) nm(Y) dbnm(D) as(Z) indexed_opt(I)
                     as(Z) on_opt(N) using_opt(U). {
     if( X==0 && Z.n==0 && N==0 && U==0 ){
       A = F;
+    }else if( F->nSrc==1 ){
+      A = sqlite3SrcListAppendFromTerm(pParse,X,0,0,&Z,0,N,U);
+      if( A ){
+        struct SrcList_item *pNew = &A->a[A->nSrc-1];
+        struct SrcList_item *pOld = F->a;
+        pNew->zName = pOld->zName;
+        pNew->zDatabase = pOld->zDatabase;
+        pOld->zName = pOld->zDatabase = 0;
+      }
+      sqlite3SrcListDelete(pParse->db, F);
     }else{
       Select *pSubquery;
       sqlite3SrcListShiftJoinType(F);
-      pSubquery = sqlite3SelectNew(pParse,0,F,0,0,0,0,0,0,0);
+      pSubquery = sqlite3SelectNew(pParse,0,F,0,0,0,0,SF_NestedFrom,0,0);
       A = sqlite3SrcListAppendFromTerm(pParse,X,0,0,&Z,pSubquery,N,U);
     }
   }
index 2568cf70816645a2471ed45971a5b8d7b727a7b4..711669ae8040a1580bc83150e2bb889bd670581b 100644 (file)
@@ -55,7 +55,7 @@ Select *sqlite3SelectNew(
   ExprList *pGroupBy,   /* the GROUP BY clause */
   Expr *pHaving,        /* the HAVING clause */
   ExprList *pOrderBy,   /* the ORDER BY clause */
-  int isDistinct,       /* true if the DISTINCT keyword is present */
+  u16 selFlags,         /* Flag parameters, such as SF_Distinct */
   Expr *pLimit,         /* LIMIT value.  NULL means not used */
   Expr *pOffset         /* OFFSET value.  NULL means no offset */
 ){
@@ -79,7 +79,7 @@ Select *sqlite3SelectNew(
   pNew->pGroupBy = pGroupBy;
   pNew->pHaving = pHaving;
   pNew->pOrderBy = pOrderBy;
-  pNew->selFlags = isDistinct ? SF_Distinct : 0;
+  pNew->selFlags = selFlags;
   pNew->op = TK_SELECT;
   pNew->pLimit = pLimit;
   pNew->pOffset = pOffset;
index 2b58a808fb432312290c58bc0a1c142fb59dc74d..8a04ab47b026d4ea72ce8215ea63f0767c3eae85 100644 (file)
@@ -2102,6 +2102,7 @@ struct Select {
 #define SF_UseSorter       0x0040  /* Sort using a sorter */
 #define SF_Values          0x0080  /* Synthesized from VALUES clause */
 #define SF_Materialize     0x0100  /* Force materialization of views */
+#define SF_NestedFrom      0x0200  /* Part of a parenthesized FROM clause */
 
 
 /*
@@ -2814,7 +2815,7 @@ Index *sqlite3CreateIndex(Parse*,Token*,Token*,SrcList*,ExprList*,int,Token*,
 void sqlite3DropIndex(Parse*, SrcList*, int);
 int sqlite3Select(Parse*, Select*, SelectDest*);
 Select *sqlite3SelectNew(Parse*,ExprList*,SrcList*,Expr*,ExprList*,
-                         Expr*,ExprList*,int,Expr*,Expr*);
+                         Expr*,ExprList*,u16,Expr*,Expr*);
 void sqlite3SelectDelete(sqlite3*, Select*);
 Table *sqlite3SrcListLookup(Parse*, SrcList*);
 int sqlite3IsReadOnly(Parse*, Table*, int);
index a7d5edb3fd4ddea0fd2b490b3babfba0a7c4b7d0..3bf1790132a292b724b26569da0961b8ad8dd6d6 100644 (file)
@@ -290,6 +290,20 @@ do_test where8-3.15 {
   }
 } {I I I I I I I I I I II II II II II II II II II II III III III III III 9 1}
 
+
+do_test where8-3.21 {
+  execsql_status {
+    SELECT a, d FROM t1, (t2) WHERE (a=d OR b=e) AND a<5 ORDER BY a
+  }
+} {1 1 2 2 3 3 4 2 4 4 0 0}
+do_test where8-3.22 {
+  execsql_status {
+    SELECT a, d FROM ((((((t1))), (((t2))))))
+     WHERE (a=d OR b=e) AND a<5 ORDER BY a
+  }
+} {1 1 2 2 3 3 4 2 4 4 0 0}
+
+
 #-----------------------------------------------------------------------
 # The following tests - where8-4.* - verify that adding or removing 
 # indexes does not change the results returned by various queries.
index d618208ad672f3b692246a904929fc398895ac80..a5c1d3935afa1c291a5974a1730fe7cede3e325f 100644 (file)
@@ -232,7 +232,7 @@ do_test where9-1.3.3 {
 } {90 91 92 97 scan 98 sort 0}
 do_test where9-1.3.4 {
   count_steps {
-    SELECT a FROM t4
+    SELECT a FROM (t4)
      WHERE (b IS NULL AND c NOT NULL AND d NOT NULL)
         OR (b NOT NULL AND c NOT NULL AND d IS NULL)
         OR (b NOT NULL AND c IS NULL AND d NOT NULL)
@@ -876,5 +876,21 @@ do_test where9-8.1 {
      ORDER BY +a;
   }
 } {2 3 4 5 {} {} 5 55 3 4 5 6 2 4 5 55}
+do_test where9-8.2 {
+  db eval {
+    SELECT *
+      FROM t81 LEFT JOIN (t82) ON y=b JOIN t83
+     WHERE c==p OR d==p
+     ORDER BY +a;
+  }
+} {2 3 4 5 {} {} 5 55 3 4 5 6 2 4 5 55}
+do_test where9-8.3 {
+  db eval {
+    SELECT *
+      FROM (t81) LEFT JOIN (main.t82) ON y=b JOIN t83
+     WHERE c==p OR d==p
+     ORDER BY +a;
+  }
+} {2 3 4 5 {} {} 5 55 3 4 5 6 2 4 5 55}
 
 finish_test