From: dan Date: Thu, 27 Feb 2020 15:07:16 +0000 (+0000) Subject: Optimization for "SELECT min(x) FROM tbl" where "x" is indexed and NOT NULL. This... X-Git-Tag: version-3.32.0~144 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=67e2bb92df88c2497a5bbbe82b3e3be4fce8b6fc;p=thirdparty%2Fsqlite.git Optimization for "SELECT min(x) FROM tbl" where "x" is indexed and NOT NULL. This also allows similar queries on NOT NULL virtual table columns to be optimized. FossilOrigin-Name: 59726777934e201d94e99ca693f0fda4ebfb1c7883d0258ce542f63f9924c28c --- diff --git a/manifest b/manifest index 28c9ec3b41..909d8864bf 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Extra\szero\sterminators\son\sthe\send\sof\sthe\sblank\sfilename\sreturned\sby\nsqlite3PagerFilename()\sfor\san\sin-memory\sdatabase.\s\sThis\shelps\sthe\sresult\nwork\sbetter\swith\ssqlite3_filename_journal()\sand\ssimilar\sfunctions. -D 2020-02-27T13:54:18.189 +C Optimization\sfor\s"SELECT\smin(x)\sFROM\stbl"\swhere\s"x"\sis\sindexed\sand\sNOT\sNULL.\sThis\salso\sallows\ssimilar\squeries\son\sNOT\sNULL\svirtual\stable\scolumns\sto\sbe\soptimized. +D 2020-02-27T15:07:16.973 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724 @@ -531,7 +531,7 @@ F src/printf.c 9be6945837c839ba57837b4bc3af349eba630920fa5532aa518816defe42a7d4 F src/random.c 80f5d666f23feb3e6665a6ce04c7197212a88384 F src/resolve.c 38e3a5636f5bdc92e3683e4cafbba6418c0aa15e0d89ca5b28bd0b621dbb80bf F src/rowset.c d977b011993aaea002cab3e0bb2ce50cf346000dff94e944d547b989f4b1fe93 -F src/select.c 466f57380528f1d7deeef87a3af09e0ad806fa2eef5e97384ec9376727fdd847 +F src/select.c ba2280da7ead581518870d7c4b91e4a4cca529182f4ff0a77ee7b0dd11339598 F src/shell.c.in c2e20c43a44fb5588a6c27ce60589538fbf4794fd7686f5b2598eca22eaae1fa F src/sqlite.h.in 802957feeb249ede54f8dfe99b72aa19e70a0b7737969c46e625dc2f9f2d42b0 F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8 @@ -994,6 +994,7 @@ F test/fts4merge2.test 5faa558d1b672f82b847d2a337465fa745e46891 F test/fts4merge3.test 8d9ccb4a3d41c4c617a149d6c4b13ad02de797d0 F test/fts4merge4.test d895b1057a7798b67e03455d0fa50e9ea836c47b F test/fts4merge5.test 69932d85cda8a1c4dcfb742865900ed8fbda51724b8cf9a45bbe226dfd06c596 +F test/fts4min.test 1c11e4bde16674a0c795953509cbc3731a7d9cbd1ddc7f35467bf39d632d749f F test/fts4noti.test 5553d7bb2e20bf4a06b23e849352efc022ce6309 F test/fts4onepass.test d69ddc4ee3415e40b0c5d1d0408488a87614d4f63ba9c44f3e52db541d6b7cc7 F test/fts4opt.test 0fd0cc84000743ff2a883b9b84b4a5be07249f0ba790c8848a757164cdd46b2a @@ -1859,7 +1860,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 bfb09371d452d5d4dacab2ec476880bc729952f44ac0e5de90ea7ba203243c8c -R 5ea099496e5d0aac03718d52a5e75d65 -U drh -Z 3b819f0341c5afa503f11379a99ca43e +P 63e533d28e87bbb10e0c611de4b79d22aae291b163fe59d1f95dcad9ab3939e4 +R 2f24ac4a9d4b9d59e52da72bc0c93415 +U dan +Z de649ec613ed7c522a2438da247b65f6 diff --git a/manifest.uuid b/manifest.uuid index 70e8738c52..bdfbdc0d6d 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -63e533d28e87bbb10e0c611de4b79d22aae291b163fe59d1f95dcad9ab3939e4 \ No newline at end of file +59726777934e201d94e99ca693f0fda4ebfb1c7883d0258ce542f63f9924c28c \ No newline at end of file diff --git a/src/select.c b/src/select.c index 231027b61d..a00abcc3de 100644 --- a/src/select.c +++ b/src/select.c @@ -4477,7 +4477,9 @@ static u8 minMaxQuery(sqlite3 *db, Expr *pFunc, ExprList **ppMinMax){ zFunc = pFunc->u.zToken; if( sqlite3StrICmp(zFunc, "min")==0 ){ eRet = WHERE_ORDERBY_MIN; - sortFlags = KEYINFO_ORDER_BIGNULL; + if( sqlite3ExprCanBeNull(pEList->a[0].pExpr) ){ + sortFlags = KEYINFO_ORDER_BIGNULL; + } }else if( sqlite3StrICmp(zFunc, "max")==0 ){ eRet = WHERE_ORDERBY_MAX; sortFlags = KEYINFO_ORDER_DESC; diff --git a/test/fts4min.test b/test/fts4min.test new file mode 100644 index 0000000000..ca63b39617 --- /dev/null +++ b/test/fts4min.test @@ -0,0 +1,53 @@ +# 2020 February 27 +# +# The author disclaims copyright to this source code. In place of +# a legal notice, here is a blessing: +# +# May you do good and not evil. +# May you find forgiveness for yourself and forgive others. +# May you share freely, never taking more than you give. +# +#************************************************************************* +# + +set testdir [file dirname $argv0] +source $testdir/tester.tcl +source $testdir/fts3_common.tcl +set ::testprefix fts4min + +# If SQLITE_ENABLE_FTS3 is defined, omit this file. +ifcapable !fts3 { + finish_test + return +} + +#------------------------------------------------------------------ +do_execsql_test 0.0 { + CREATE TABLE t1(a NOT NULL, b); + CREATE INDEX i1 ON t1(a); +} + +do_execsql_test 1.0 { + CREATE VIRTUAL TABLE ft USING fts3(c); + INSERT INTO ft(docid, c) VALUES(22, 'hello world'); + INSERT INTO ft(docid, c) VALUES(44, 'hello world'); + INSERT INTO ft(docid, c) VALUES(11, 'hello world'); +} + +do_eqp_test 1.1.1 { + SELECT max(rowid) FROM ft +} {VIRTUAL TABLE INDEX 0:DESC} + +do_eqp_test 1.1.2 { + SELECT min(rowid) FROM ft +} {VIRTUAL TABLE INDEX 0:ASC} + +do_execsql_test 1.2.1 { + SELECT max(rowid) FROM ft +} {44} + +do_execsql_test 1.2.2 { + SELECT min(rowid) FROM ft +} {11} + +finish_test