From: drh <> Date: Wed, 24 Mar 2021 19:44:01 +0000 (+0000) Subject: Comment improvements to on the distinct-agg optimization. Show a line in X-Git-Tag: version-3.36.0~288 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=9be1339faf9dc7d0462143c56fa2f369dcde3f8c;p=thirdparty%2Fsqlite.git Comment improvements to on the distinct-agg optimization. Show a line in the EQP output when using an ephemeral table to implement DISTINCT on an aggregate. FossilOrigin-Name: 037ca79e6032ca962b4f6182187bc12a7d91170d73630c8cd6fb191d2c183ee4 --- diff --git a/manifest b/manifest index d4587fd8b3..0413a9b465 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Improvements\sto\sdistinct\saggregates\ssuch\sthat\sthey\scan\ssometimes\savoid\nusing\san\sephermeral\stable\sto\stest\sfor\sduplicates\sif\sthe\scolumn\sthat\sis\ndistinct\sis\spart\sof\san\sindex. -D 2021-03-24T17:28:11.642 +C Comment\simprovements\sto\son\sthe\sdistinct-agg\soptimization.\s\sShow\sa\sline\sin\nthe\sEQP\soutput\swhen\susing\san\sephemeral\stable\sto\simplement\sDISTINCT\son\san\naggregate. +D 2021-03-24T19:44:01.340 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724 @@ -542,7 +542,7 @@ F src/printf.c 78fabb49b9ac9a12dd1c89d744abdc9b67fd3205e62967e158f78b965a29ec4b F src/random.c 80f5d666f23feb3e6665a6ce04c7197212a88384 F src/resolve.c d95db73d3e6a5c689e5f6604b4d2521350e45f2a0f0f84f5a2dc2bfee56580a0 F src/rowset.c ba9515a922af32abe1f7d39406b9d35730ed65efab9443dc5702693b60854c92 -F src/select.c 9109ca4a3179eb46770e10c04f01fd226751ccf0caeea8db58000e3371f9fa21 +F src/select.c 22b0309a334e683cb453bfb16ca5cd423bfebc16b3360fe424707baf900b5919 F src/shell.c.in dcce260883836c9b58847505fbccce8d5546af925046f7dacd9443e922ece036 F src/sqlite.h.in 3426a080ea1f222a73e3bd91e7eacbd30570a0117c03d42c6dde606f33e5e318 F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8 @@ -843,7 +843,7 @@ F test/descidx1.test edc8adee58d491b06c7157c50364eaf1c3605c9c19f8093cb1ea2b6184f F test/descidx2.test a0ba347037ff3b811f4c6ceca5fd0f9d5d72e74e59f2d9de346a9d2f6ad78298 F test/descidx3.test 953c831df7ea219c73826dfbf2f6ee02d95040725aa88ccb4fa43d1a1999b926 F test/diskfull.test 106391384780753ea6896b7b4f005d10e9866b6e -F test/distinct.test e7d0cf371944dd0cbedff86420744e2f1ea2b528156451c97eb6ff41a99b9236 +F test/distinct.test eefe5a8e47fcb761aaa745838e355ab28586f9f75786a1c098016881344b2a5e F test/distinct2.test cd1d15a4a2abf579298f7161e821ed50c0119136fe0424db85c52cf0adc230d1 F test/distinctagg.test fd74c3783700f1d99c67a5d906bba97fb6650f4559f3ea7b1873f793ffc601c9 F test/e_blobbytes.test 439a945953b35cb6948a552edaec4dc31fd70a05 @@ -1911,8 +1911,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 26b005a95e4f3e378e3bc40f57321ffbab72b6fc990d13b56b3121990d325f63 0817cf2ec08fdefd3c1d41790df7b5d6d490767757b44bb0229694023c8e40fc -R 299a3406efa01e76d5f6f5a54ae9efc6 -T +closed 0817cf2ec08fdefd3c1d41790df7b5d6d490767757b44bb0229694023c8e40fc +P ef4ac0ddd297bbd38351410c5a387e1628561b3f1bec9e4c2c9d76fbe29f955a +R dcb5dee51b0acb34e00007490cfee341 U drh -Z 8f54305fe91515917058141910a21763 +Z c32591fb9c8184cbc930f8b40bd7a719 diff --git a/manifest.uuid b/manifest.uuid index f3b8f43662..3e4f52ae91 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ef4ac0ddd297bbd38351410c5a387e1628561b3f1bec9e4c2c9d76fbe29f955a \ No newline at end of file +037ca79e6032ca962b4f6182187bc12a7d91170d73630c8cd6fb191d2c183ee4 \ No newline at end of file diff --git a/src/select.c b/src/select.c index b94efd5f3d..e7ae01aca7 100644 --- a/src/select.c +++ b/src/select.c @@ -748,6 +748,9 @@ static void codeOffset( ** as follows: ** ** WHERE_DISTINCT_UNORDERED/WHERE_DISTINCT_NOOP: +** Build an ephemeral table that contains all entries seen before and +** skip entries which have been seen before. +** ** Parameter iTab is the cursor number of an ephemeral table that must ** be opened before the VM code generated by this routine is executed. ** The ephemeral cursor table is queried for a record identical to the @@ -758,20 +761,21 @@ static void codeOffset( ** The returned value in this case is a copy of parameter iTab. ** ** WHERE_DISTINCT_ORDERED: -** In this case rows are being delivered sorted order sorted. The ephermal -** table is not required in this case. Instead, the current set of -** registers are compared to previous row. If they match, the new row +** In this case rows are being delivered sorted order. The ephermal +** table is not required. Instead, the current set of values +** is compared against previous row. If they match, the new row ** is not distinct and control jumps to VM address addrRepeat. Otherwise, ** the VM program proceeds with processing the new row. ** ** The returned value in this case is the register number of the first ** in an array of registers used to store the previous result row so that -** it can be compared to the next. The caller must ensure that this cell -** is initialized to NULL and has the "clear" flag set. +** it can be compared to the next. The caller must ensure that this +** register is initialized to NULL. (The fixDistinctOpenEph() routine +** will take care of this initialization.) ** ** WHERE_DISTINCT_UNIQUE: ** In this case it has already been determined that the rows are distinct. -** No special action is required. The return value is always zero. +** No special action is required. The return value is zero. ** ** Parameter pEList is the list of expressions used to generated the ** contents of each row. It is used by this routine to determine (a) @@ -841,25 +845,27 @@ static int codeDistinct( } /* -** A call to this function must be made for each call to codeDistinct(). -** Parameter is passed the value returned by that call to codeDistinct(), -** and iOpenEphAddr the address of the instruction used to open the -** ephemeral table (that may be) used by codeDistinct(). +** This routine runs after codeDistinct(). It makes necessary +** adjustments to the OP_OpenEphemeral opcode that the codeDistinct() +** routine made use of. This processing must be done separately since +** sometimes codeDistinct is called before the OP_OpenEphemeral is actually +** laid down. ** -** Argument eTnctType is passed the strategy to be used for any DISTINCT -** operation, as returned by sqlite3WhereIsDistinct(). If the strategy -** is WHERE_DISTINCT_NOOP or WHERE_DISTINCT_UNORDERED, this function is -** a no-op. Otherwise: +** WHERE_DISTINCT_NOOP: +** WHERE_DISTINCT_UNORDERED: ** -** WHERE_DISTINCT_UNIQUE: -** In this case the ephemeral table is not required. So instruction -** iOpenEphAddr is replaced by an OP_Noop. +** No adjustments necessary. This function is a no-op. ** -** WHERE_DISTINCT_ORDERED: -** In this case the ephemeral table is not required. The instruction -** iOpenEphAddr is replaced by an OP_Null instruction to set register -** iVal to a NULL value with the "clear" flag set (see comments above -** codeDistinct() for details). +** WHERE_DISTINCT_UNIQUE: +** +** The ephemeral table is not needed. So change the +** OP_OpenEphemeral opcode into an OP_Noop. +** +** WHERE_DISTINCT_ORDERED: +** +** The ephemeral table is not needed. But we do need register +** iVal to be initialized to NULL. So change the OP_OpenEphemeral +** into an OP_Null on the iVal register. */ static void fixDistinctOpenEph( Parse *pParse, /* Parsing and code generating context */ @@ -870,6 +876,9 @@ static void fixDistinctOpenEph( if( eTnctType==WHERE_DISTINCT_UNIQUE || eTnctType==WHERE_DISTINCT_ORDERED ){ Vdbe *v = pParse->pVdbe; sqlite3VdbeChangeToNoop(v, iOpenEphAddr); + if( sqlite3VdbeGetOp(v, iOpenEphAddr+1)->opcode==OP_Explain ){ + sqlite3VdbeChangeToNoop(v, iOpenEphAddr+1); + } if( eTnctType==WHERE_DISTINCT_ORDERED ){ /* Change the OP_OpenEphemeral to an OP_Null that sets the MEM_Cleared ** bit on the first register of the previous value. This will cause the @@ -5714,6 +5723,8 @@ static void resetAccumulator(Parse *pParse, AggInfo *pAggInfo){ KeyInfo *pKeyInfo = sqlite3KeyInfoFromExprList(pParse, pE->x.pList,0,0); pFunc->iDistAddr = sqlite3VdbeAddOp4(v, OP_OpenEphemeral, pFunc->iDistinct, 0, 0, (char*)pKeyInfo, P4_KEYINFO); + ExplainQueryPlan((pParse, 0, "USE TEMP B-TREE FOR %s(DISTINCT)", + pFunc->pFunc->zName)); } } } diff --git a/test/distinct.test b/test/distinct.test index f6f3c6cdce..19da4fd61c 100644 --- a/test/distinct.test +++ b/test/distinct.test @@ -30,12 +30,11 @@ proc is_distinct_noop {sql} { set program1 [list] set program2 [list] db eval "EXPLAIN $sql1" { - if {$opcode != "Noop"} { lappend program1 $opcode } + if {$opcode != "Noop" && $opcode != "Explain"} { lappend program1 $opcode } } db eval "EXPLAIN $sql2" { - if {$opcode != "Noop"} { lappend program2 $opcode } + if {$opcode != "Noop" && $opcode != "Explain"} { lappend program2 $opcode } } - return [expr {$program1==$program2}] }