OLD | NEW |
(Empty) | |
| 1 # 2012 September 18 |
| 2 # |
| 3 # The author disclaims copyright to this source code. In place of |
| 4 # a legal notice, here is a blessing: |
| 5 # |
| 6 # May you do good and not evil. |
| 7 # May you find forgiveness for yourself and forgive others. |
| 8 # May you share freely, never taking more than you give. |
| 9 # |
| 10 #*********************************************************************** |
| 11 # |
| 12 |
| 13 set testdir [file dirname $argv0] |
| 14 source $testdir/tester.tcl |
| 15 set testprefix in5 |
| 16 |
| 17 do_test in5-1.1 { |
| 18 execsql { |
| 19 CREATE TABLE t1x(x INTEGER PRIMARY KEY); |
| 20 INSERT INTO t1x VALUES(1),(3),(5),(7),(9); |
| 21 CREATE TABLE t1y(y INTEGER UNIQUE); |
| 22 INSERT INTO t1y VALUES(2),(4),(6),(8); |
| 23 CREATE TABLE t1z(z TEXT UNIQUE); |
| 24 INSERT INTO t1z VALUES('a'),('c'),('e'),('g'); |
| 25 CREATE TABLE t2(a INTEGER, b INTEGER, c TEXT, d TEXT); |
| 26 INSERT INTO t2 VALUES(1,2,'a','12a'),(1,2,'b','12b'), |
| 27 (2,3,'g','23g'),(3,5,'c','35c'), |
| 28 (4,6,'h','46h'),(5,6,'e','56e'); |
| 29 CREATE TABLE t3x AS SELECT x FROM t1x; |
| 30 CREATE TABLE t3y AS SELECT y FROM t1y; |
| 31 CREATE TABLE t3z AS SELECT z FROM t1z; |
| 32 SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z ORDER BY c; |
| 33 } |
| 34 } {12a 56e} |
| 35 do_test in5-1.2 { |
| 36 execsql { |
| 37 SELECT d FROM t2 WHERE a IN t1y AND b IN t1x AND c IN t1z ORDER BY d; |
| 38 } |
| 39 } {23g} |
| 40 do_test in5-1.3 { |
| 41 execsql { |
| 42 SELECT d FROM t2 WHERE a IN t3x AND b IN t3y AND c IN t3z ORDER BY d; |
| 43 } |
| 44 } {12a 56e} |
| 45 |
| 46 |
| 47 do_test in5-2.1 { |
| 48 execsql { |
| 49 CREATE INDEX t2abc ON t2(a,b,c); |
| 50 SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z ORDER BY d; |
| 51 } |
| 52 } {12a 56e} |
| 53 do_test in5-2.2 { |
| 54 execsql { |
| 55 SELECT d FROM t2 WHERE a IN t1y AND b IN t1x AND c IN t1z ORDER BY d; |
| 56 } |
| 57 } {23g} |
| 58 do_test in5-2.3 { |
| 59 regexp {OpenEphemeral} [db eval { |
| 60 EXPLAIN SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z |
| 61 }] |
| 62 } {0} |
| 63 do_test in5-2.4 { |
| 64 execsql { |
| 65 SELECT d FROM t2 WHERE a IN t3x AND b IN t3y AND c IN t3z ORDER BY d; |
| 66 } |
| 67 } {12a 56e} |
| 68 do_test in5-2.5.1 { |
| 69 regexp {OpenEphemeral} [db eval { |
| 70 EXPLAIN SELECT d FROM t2 WHERE a IN t3x AND b IN t1y AND c IN t1z |
| 71 }] |
| 72 } {1} |
| 73 do_test in5-2.5.2 { |
| 74 regexp {OpenEphemeral} [db eval { |
| 75 EXPLAIN SELECT d FROM t2 WHERE a IN t1x AND b IN t3y AND c IN t1z |
| 76 }] |
| 77 } {1} |
| 78 do_test in5-2.5.3 { |
| 79 regexp {OpenEphemeral} [db eval { |
| 80 EXPLAIN SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t3z |
| 81 }] |
| 82 } {1} |
| 83 |
| 84 do_test in5-3.1 { |
| 85 execsql { |
| 86 DROP INDEX t2abc; |
| 87 CREATE INDEX t2ab ON t2(a,b); |
| 88 SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z ORDER BY d; |
| 89 } |
| 90 } {12a 56e} |
| 91 do_test in5-3.2 { |
| 92 execsql { |
| 93 SELECT d FROM t2 WHERE a IN t1y AND b IN t1x AND c IN t1z ORDER BY d; |
| 94 } |
| 95 } {23g} |
| 96 do_test in5-3.3 { |
| 97 regexp {OpenEphemeral} [db eval { |
| 98 EXPLAIN SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z |
| 99 }] |
| 100 } {0} |
| 101 |
| 102 do_test in5-4.1 { |
| 103 execsql { |
| 104 DROP INDEX t2ab; |
| 105 CREATE INDEX t2abcd ON t2(a,b,c,d); |
| 106 SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z ORDER BY d; |
| 107 } |
| 108 } {12a 56e} |
| 109 do_test in5-4.2 { |
| 110 execsql { |
| 111 SELECT d FROM t2 WHERE a IN t1y AND b IN t1x AND c IN t1z ORDER BY d; |
| 112 } |
| 113 } {23g} |
| 114 do_test in5-4.3 { |
| 115 regexp {OpenEphemeral} [db eval { |
| 116 EXPLAIN SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z |
| 117 }] |
| 118 } {0} |
| 119 |
| 120 |
| 121 do_test in5-5.1 { |
| 122 execsql { |
| 123 DROP INDEX t2abcd; |
| 124 CREATE INDEX t2cbad ON t2(c,b,a,d); |
| 125 SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z ORDER BY d; |
| 126 } |
| 127 } {12a 56e} |
| 128 do_test in5-5.2 { |
| 129 execsql { |
| 130 SELECT d FROM t2 WHERE a IN t1y AND b IN t1x AND c IN t1z ORDER BY d; |
| 131 } |
| 132 } {23g} |
| 133 do_test in5-5.3 { |
| 134 regexp {OpenEphemeral} [db eval { |
| 135 EXPLAIN SELECT d FROM t2 WHERE a IN t1x AND b IN t1y AND c IN t1z |
| 136 }] |
| 137 } {0} |
| 138 |
| 139 #------------------------------------------------------------------------- |
| 140 # At one point SQLite was removing the DISTINCT keyword from expressions |
| 141 # similar to: |
| 142 # |
| 143 # <expr1> IN (SELECT DISTINCT <expr2> FROM...) |
| 144 # |
| 145 # However, there are a few obscure cases where this is incorrect. For |
| 146 # example, if the SELECT features a LIMIT clause, or if the collation |
| 147 # sequence or affinity used by the DISTINCT does not match the one used |
| 148 # by the IN(...) expression. |
| 149 # |
| 150 do_execsql_test 6.1.1 { |
| 151 CREATE TABLE t1(a COLLATE nocase); |
| 152 INSERT INTO t1 VALUES('one'); |
| 153 INSERT INTO t1 VALUES('ONE'); |
| 154 } |
| 155 do_execsql_test 6.1.2 { |
| 156 SELECT count(*) FROM t1 WHERE a COLLATE BINARY IN (SELECT DISTINCT a FROM t1) |
| 157 } {1} |
| 158 |
| 159 do_execsql_test 6.2.1 { |
| 160 CREATE TABLE t3(a, b); |
| 161 INSERT INTO t3 VALUES(1, 1); |
| 162 INSERT INTO t3 VALUES(1, 2); |
| 163 INSERT INTO t3 VALUES(1, 3); |
| 164 INSERT INTO t3 VALUES(2, 4); |
| 165 INSERT INTO t3 VALUES(2, 5); |
| 166 INSERT INTO t3 VALUES(2, 6); |
| 167 INSERT INTO t3 VALUES(3, 7); |
| 168 INSERT INTO t3 VALUES(3, 8); |
| 169 INSERT INTO t3 VALUES(3, 9); |
| 170 } |
| 171 do_execsql_test 6.2.2 { |
| 172 SELECT count(*) FROM t3 WHERE b IN (SELECT DISTINCT a FROM t3 LIMIT 5); |
| 173 } {3} |
| 174 do_execsql_test 6.2.3 { |
| 175 SELECT count(*) FROM t3 WHERE b IN (SELECT a FROM t3 LIMIT 5); |
| 176 } {2} |
| 177 |
| 178 do_execsql_test 6.3.1 { |
| 179 CREATE TABLE x1(a); |
| 180 CREATE TABLE x2(b); |
| 181 INSERT INTO x1 VALUES(1), (1), (2); |
| 182 INSERT INTO x2 VALUES(1), (2); |
| 183 SELECT count(*) FROM x2 WHERE b IN (SELECT DISTINCT a FROM x1 LIMIT 2); |
| 184 } {2} |
| 185 |
| 186 finish_test |
OLD | NEW |