join_index.slt 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771
  1. # Copyright Materialize, Inc. and contributors. All rights reserved.
  2. #
  3. # Use of this software is governed by the Business Source License
  4. # included in the LICENSE file at the root of this repository.
  5. #
  6. # As of the Change Date specified in that file, in accordance with
  7. # the Business Source License, use of this software will be governed
  8. # by the Apache License, Version 2.0.
  9. simple conn=mz_system,user=mz_system
  10. ALTER SYSTEM SET unsafe_enable_table_keys = true
  11. ----
  12. COMPLETE 0
  13. statement ok
  14. DROP TABLE IF EXISTS foo;
  15. statement ok
  16. DROP TABLE IF EXISTS bar;
  17. statement ok
  18. CREATE TABLE foo(a int, b int)
  19. statement ok
  20. INSERT INTO foo VALUES (1, 2), (-1, 4), (null, 3)
  21. statement ok
  22. CREATE TABLE bar(a int, b int)
  23. statement ok
  24. INSERT INTO bar VALUES (1, 3), (-1, null), (null, 5)
  25. # no indexes other than the default foo(a,b) and bar(a,b)
  26. query T multiline
  27. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR select * from foo inner join bar on foo.a = bar.a where foo.a = 1
  28. ----
  29. Explained Query:
  30. CrossJoin type=differential // { arity: 4 }
  31. implementation
  32. %0:foo[×]ef » %1:bar[×]ef
  33. ArrangeBy keys=[[]] // { arity: 2 }
  34. Filter (#0{a} = 1) // { arity: 2 }
  35. ReadStorage materialize.public.foo // { arity: 2 }
  36. ArrangeBy keys=[[]] // { arity: 2 }
  37. Filter (#0{a} = 1) // { arity: 2 }
  38. ReadStorage materialize.public.bar // { arity: 2 }
  39. Source materialize.public.foo
  40. filter=((#0{a} = 1))
  41. Source materialize.public.bar
  42. filter=((#0{a} = 1))
  43. Target cluster: quickstart
  44. EOF
  45. query IIII
  46. select * from foo inner join bar on foo.a = bar.a where foo.a = 1
  47. ----
  48. 1
  49. 2
  50. 1
  51. 3
  52. # no indexes other than the default foo(a,b) and bar(a,b)
  53. query T multiline
  54. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR select * from foo inner join bar on foo.a = abs(bar.a) where mod(foo.a, 2) = 1
  55. ----
  56. Explained Query:
  57. Join on=(#0{a} = abs(#2{a})) type=differential // { arity: 4 }
  58. implementation
  59. %0:foo[#0{a}]Kef » %1:bar[abs(#0{a})]Kef
  60. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  61. Filter (1 = (#0{a} % 2)) // { arity: 2 }
  62. ReadStorage materialize.public.foo // { arity: 2 }
  63. ArrangeBy keys=[[abs(#0{a})]] // { arity: 2 }
  64. Filter (1 = (abs(#0{a}) % 2)) // { arity: 2 }
  65. ReadStorage materialize.public.bar // { arity: 2 }
  66. Source materialize.public.foo
  67. filter=((1 = (#0{a} % 2)))
  68. Source materialize.public.bar
  69. filter=((1 = (abs(#0{a}) % 2)))
  70. Target cluster: quickstart
  71. EOF
  72. query IIII
  73. select * from foo inner join bar on foo.a = abs(bar.a) where mod(foo.a, 2) = 1
  74. ----
  75. 1
  76. 2
  77. -1
  78. NULL
  79. 1
  80. 2
  81. 1
  82. 3
  83. # Test that equivalence propagation can propagate across inputs of a join.
  84. # no indexes other than the default foo(a,b) and bar(a,b)
  85. query T multiline
  86. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR select * from (select * from foo where a = 1) filtered_foo, bar where filtered_foo.a = bar.a
  87. ----
  88. Explained Query:
  89. CrossJoin type=differential // { arity: 4 }
  90. implementation
  91. %0:foo[×]ef » %1:bar[×]ef
  92. ArrangeBy keys=[[]] // { arity: 2 }
  93. Filter (#0{a} = 1) // { arity: 2 }
  94. ReadStorage materialize.public.foo // { arity: 2 }
  95. ArrangeBy keys=[[]] // { arity: 2 }
  96. Filter (#0{a} = 1) // { arity: 2 }
  97. ReadStorage materialize.public.bar // { arity: 2 }
  98. Source materialize.public.foo
  99. filter=((#0{a} = 1))
  100. Source materialize.public.bar
  101. filter=((#0{a} = 1))
  102. Target cluster: quickstart
  103. EOF
  104. query IIII
  105. select * from (select * from foo where a = 1) filtered_foo, bar where filtered_foo.a = bar.a
  106. ----
  107. 1
  108. 2
  109. 1
  110. 3
  111. statement ok
  112. CREATE INDEX foo_idx on foo(a);
  113. statement ok
  114. CREATE INDEX bar_idx on bar(a);
  115. statement ok
  116. CREATE TABLE baz(a int primary key, b int)
  117. statement ok
  118. INSERT INTO baz VALUES (3, 0), (5, 2)
  119. # indexes exist on foo(a), bar(a), and baz(a). baz(a) is a unique key
  120. query T multiline
  121. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  122. select foo.a, baz.b
  123. from foo, bar, baz
  124. where foo.a = bar.a
  125. and baz.a = bar.b
  126. ----
  127. Explained Query:
  128. Project (#0{a}, #5{b}) // { arity: 2 }
  129. Join on=(#0{a} = #2{a} AND #3{b} = #4{a}) type=delta // { arity: 6 }
  130. implementation
  131. %0:foo » %1:bar[#0{a}]KA » %2:baz[#0{a}]UK
  132. %1:bar » %2:baz[#0{a}]UK » %0:foo[#0{a}]KA
  133. %2:baz » %1:bar[#1{b}]K » %0:foo[#0{a}]KA
  134. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  135. ReadIndex on=foo foo_idx=[delta join 1st input (full scan)] // { arity: 2 }
  136. ArrangeBy keys=[[#0{a}], [#1{b}]] // { arity: 2 }
  137. Filter (#0{a}) IS NOT NULL AND (#1{b}) IS NOT NULL // { arity: 2 }
  138. ReadIndex on=bar bar_idx=[*** full scan ***] // { arity: 2 }
  139. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  140. ReadStorage materialize.public.baz // { arity: 2 }
  141. Source materialize.public.baz
  142. Used Indexes:
  143. - materialize.public.foo_idx (delta join 1st input (full scan))
  144. - materialize.public.bar_idx (*** full scan ***)
  145. Target cluster: quickstart
  146. EOF
  147. query II
  148. select foo.a, baz.b
  149. from foo, bar, baz
  150. where foo.a = bar.a
  151. and baz.a = bar.b
  152. ----
  153. 1
  154. 0
  155. statement ok
  156. DROP TABLE baz
  157. statement ok
  158. CREATE TABLE baz(a int, b int)
  159. statement ok
  160. INSERT INTO baz VALUES (3, 0), (5, 2), (null, 6)
  161. statement ok
  162. CREATE INDEX baz_idx on baz(a);
  163. # indexes exist on foo(a), bar(a), and baz(a)
  164. query T multiline
  165. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  166. select foo.a, baz.b
  167. from foo, bar, baz
  168. where foo.a = bar.a
  169. and baz.a = bar.b
  170. ----
  171. Explained Query:
  172. Project (#0{a}, #5{b}) // { arity: 2 }
  173. Join on=(#0{a} = #2{a} AND #3{b} = #4{a}) type=delta // { arity: 6 }
  174. implementation
  175. %0:foo » %1:bar[#0{a}]KA » %2:baz[#0{a}]KA
  176. %1:bar » %0:foo[#0{a}]KA » %2:baz[#0{a}]KA
  177. %2:baz » %1:bar[#1{b}]K » %0:foo[#0{a}]KA
  178. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  179. ReadIndex on=foo foo_idx=[delta join 1st input (full scan)] // { arity: 2 }
  180. ArrangeBy keys=[[#0{a}], [#1{b}]] // { arity: 2 }
  181. Filter (#0{a}) IS NOT NULL AND (#1{b}) IS NOT NULL // { arity: 2 }
  182. ReadIndex on=bar bar_idx=[*** full scan ***] // { arity: 2 }
  183. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  184. ReadIndex on=baz baz_idx=[delta join lookup] // { arity: 2 }
  185. Used Indexes:
  186. - materialize.public.foo_idx (delta join 1st input (full scan))
  187. - materialize.public.bar_idx (*** full scan ***)
  188. - materialize.public.baz_idx (delta join lookup)
  189. Target cluster: quickstart
  190. EOF
  191. query II
  192. select foo.a, baz.b
  193. from foo, bar, baz
  194. where foo.a = bar.a
  195. and baz.a = bar.b
  196. ----
  197. 1
  198. 0
  199. statement ok
  200. CREATE INDEX foo_idx2 on foo(nullif(a, 0));
  201. statement ok
  202. CREATE INDEX bar_idx2 on bar(-a);
  203. # Test that when join planning uses indexes on expressions.
  204. # Protects against regression of database-issues#1290.
  205. query T multiline
  206. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  207. select foo.b, bar.b
  208. from foo, bar
  209. where nullif(foo.a, 0) = -bar.a
  210. ----
  211. Explained Query:
  212. Project (#1{b}, #3{b}) // { arity: 2 }
  213. Filter (#2{a}) IS NOT NULL // { arity: 4 }
  214. Join on=(-(#2{a}) = case when (#0{a} = 0) then null else #0{a} end) type=differential // { arity: 4 }
  215. implementation
  216. %0:foo[case when (#0{a} = 0) then null else #0{a} end]KA » %1:bar[-(#0{a})]KA
  217. ArrangeBy keys=[[case when (#0{a} = 0) then null else #0{a} end]] // { arity: 2 }
  218. ReadIndex on=foo foo_idx2=[differential join] // { arity: 2 }
  219. ArrangeBy keys=[[-(#0{a})]] // { arity: 2 }
  220. ReadIndex on=bar bar_idx2=[differential join] // { arity: 2 }
  221. Used Indexes:
  222. - materialize.public.foo_idx2 (differential join)
  223. - materialize.public.bar_idx2 (differential join)
  224. Target cluster: quickstart
  225. EOF
  226. query II
  227. select foo.b, bar.b
  228. from foo, bar
  229. where nullif(foo.a, 0) = -bar.a
  230. ----
  231. 2
  232. NULL
  233. 4
  234. 3
  235. statement ok
  236. DROP INDEX bar_idx;
  237. statement ok
  238. CREATE INDEX bar_idx3 on bar(a + 4);
  239. # In this test, there exists an index on bar(a + 4)
  240. # but not bar(a). Check that bar(a+4) is not inappropriately
  241. # substituted for bar(a) in the first equivalence.
  242. query T multiline
  243. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  244. select foo.b, bar.b, baz.b
  245. FROM bar, foo, baz
  246. where foo.a = bar.a
  247. and bar.a + 4 = baz.a
  248. ----
  249. Explained Query:
  250. Project (#3{b}, #1{b}, #5{b}) // { arity: 3 }
  251. Filter (#4{a}) IS NOT NULL // { arity: 6 }
  252. Join on=(#0{a} = #2{a} AND #4{a} = (#0{a} + 4)) type=delta // { arity: 6 }
  253. implementation
  254. %0:bar » %1:foo[#0{a}]KA » %2:baz[#0{a}]KA
  255. %1:foo » %0:bar[#0{a}]K » %2:baz[#0{a}]KA
  256. %2:baz » %0:bar[(#0{a} + 4)]KA » %1:foo[#0{a}]KA
  257. ArrangeBy keys=[[#0{a}], [(#0{a} + 4)]] // { arity: 2 }
  258. Filter (#0{a}) IS NOT NULL // { arity: 2 }
  259. ReadIndex on=bar bar_idx2=[*** full scan ***] // { arity: 2 }
  260. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  261. ReadIndex on=foo foo_idx=[delta join lookup] // { arity: 2 }
  262. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  263. ReadIndex on=baz baz_idx=[delta join lookup] // { arity: 2 }
  264. Used Indexes:
  265. - materialize.public.foo_idx (delta join lookup)
  266. - materialize.public.baz_idx (delta join lookup)
  267. - materialize.public.bar_idx2 (*** full scan ***)
  268. Target cluster: quickstart
  269. EOF
  270. mode cockroach
  271. query III rowsort
  272. select foo.b, bar.b, baz.b
  273. FROM bar, foo, baz
  274. where foo.a = bar.a
  275. and bar.a + 4 = baz.a
  276. ----
  277. 4 NULL 0
  278. 2 3 2
  279. mode standard
  280. # tests that equalities involving multi-input equalities become join conditions.
  281. query T multiline
  282. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR select foo.b, bar.b from foo, bar, (select 1 as a) const where foo.a / bar.a = const.a
  283. ----
  284. Explained Query:
  285. Project (#1{b}, #3{b}) // { arity: 2 }
  286. Join on=(1 = (#0{a} / #2{a})) type=differential // { arity: 4 }
  287. implementation
  288. %0:foo[×] » %1:bar[×]
  289. ArrangeBy keys=[[]] // { arity: 2 }
  290. ReadIndex on=foo foo_idx=[*** full scan ***] // { arity: 2 }
  291. ArrangeBy keys=[[]] // { arity: 2 }
  292. ReadIndex on=bar bar_idx2=[*** full scan ***] // { arity: 2 }
  293. Used Indexes:
  294. - materialize.public.foo_idx (*** full scan ***)
  295. - materialize.public.bar_idx2 (*** full scan ***)
  296. Target cluster: quickstart
  297. EOF
  298. mode cockroach
  299. query II rowsort
  300. select foo.b, bar.b from foo, bar, (select 1 as a) const where foo.a / bar.a = const.a
  301. ----
  302. 4 NULL
  303. 2 3
  304. mode standard
  305. query T multiline
  306. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  307. select foo.b, bar.b
  308. from foo, bar, (select -1 as a) const
  309. where foo.a / bar.a = const.a
  310. and bar.b - foo.b = foo.a / bar.a
  311. ----
  312. Explained Query:
  313. Project (#1{b}, #3{b}) // { arity: 2 }
  314. Join on=(-1 = (#3{b} - #1{b}) = (#0{a} / #2{a})) type=differential // { arity: 4 }
  315. implementation
  316. %0:foo[×] » %1:bar[×]
  317. ArrangeBy keys=[[]] // { arity: 2 }
  318. ReadIndex on=foo foo_idx=[*** full scan ***] // { arity: 2 }
  319. ArrangeBy keys=[[]] // { arity: 2 }
  320. ReadIndex on=bar bar_idx2=[*** full scan ***] // { arity: 2 }
  321. Used Indexes:
  322. - materialize.public.foo_idx (*** full scan ***)
  323. - materialize.public.bar_idx2 (*** full scan ***)
  324. Target cluster: quickstart
  325. EOF
  326. query II
  327. select foo.b, bar.b
  328. from foo, bar, (select -1 as a) const
  329. where foo.a / bar.a = const.a
  330. and bar.b - foo.b = foo.a / bar.a
  331. ----
  332. 4
  333. 3
  334. statement ok
  335. DROP INDEX baz_idx
  336. # database-issues#2449: it would be nice if this join used the indexes on bar(a+4)
  337. query T multiline
  338. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  339. select foo.b, bar.b, baz.b
  340. FROM foo, bar, baz
  341. where foo.a = bar.a
  342. and foo.a + 4 = baz.a
  343. ----
  344. Explained Query:
  345. Project (#1{b}, #3{b}, #5{b}) // { arity: 3 }
  346. Join on=(#0{a} = #2{a} AND #4{a} = (#0{a} + 4)) type=delta // { arity: 6 }
  347. implementation
  348. %0:foo » %1:bar[#0{a}]K » %2:baz[#0{a}]K
  349. %1:bar » %0:foo[#0{a}]KA » %2:baz[#0{a}]K
  350. %2:baz » %0:foo[(#0{a} + 4)]K » %1:bar[#0{a}]K
  351. ArrangeBy keys=[[#0{a}], [(#0{a} + 4)]] // { arity: 2 }
  352. Filter (#0{a}) IS NOT NULL // { arity: 2 }
  353. ReadIndex on=foo foo_idx=[*** full scan ***] // { arity: 2 }
  354. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  355. Filter (#0{a}) IS NOT NULL // { arity: 2 }
  356. ReadIndex on=bar bar_idx2=[*** full scan ***] // { arity: 2 }
  357. ArrangeBy keys=[[#0{a}]] // { arity: 2 }
  358. Filter (#0{a}) IS NOT NULL // { arity: 2 }
  359. ReadStorage materialize.public.baz // { arity: 2 }
  360. Source materialize.public.baz
  361. filter=((#0{a}) IS NOT NULL)
  362. Used Indexes:
  363. - materialize.public.foo_idx (*** full scan ***)
  364. - materialize.public.bar_idx2 (*** full scan ***)
  365. Target cluster: quickstart
  366. EOF
  367. mode cockroach
  368. query III rowsort
  369. select foo.b, bar.b, baz.b
  370. FROM bar, foo, baz
  371. where foo.a = bar.a
  372. and bar.a + 4 = baz.a
  373. ----
  374. 4 NULL 0
  375. 2 3 2
  376. mode standard
  377. statement ok
  378. CREATE TABLE t1 (f1 DOUBLE PRECISION, f2 DOUBLE PRECISION NOT NULL);
  379. statement ok
  380. CREATE INDEX t1i1 ON t1(f1);
  381. statement ok
  382. CREATE INDEX t1i2 ON t1(f2, f1);
  383. # one NULL row in t1
  384. statement ok
  385. INSERT INTO t1 VALUES (NULL, 0);
  386. # values 1 and 2 have 2 rows each in t1
  387. statement ok
  388. INSERT INTO t1 VALUES (1, 1), (1, 1), (2, 2), (2, 2), (3, 3), (4, 4), (5, 5), (6, 6), (7, 7), (8, 8);
  389. # value 9 not present in either table
  390. statement ok
  391. CREATE TABLE t2 (f1 DOUBLE PRECISION, f2 DOUBLE PRECISION NOT NULL);
  392. statement ok
  393. CREATE INDEX t2i1 ON t2(f1);
  394. statement ok
  395. CREATE INDEX i2i2 ON t2(f2, f1);
  396. # two NULL rows in t2
  397. statement ok
  398. INSERT INTO t2 VALUES (NULL, 0), (NULL, 0), (1, 1);
  399. # value 2 has 2 rows in t2
  400. statement ok
  401. INSERT INTO t2 VALUES (2, 2), (2, 2);
  402. # value 3 has no rows in t2
  403. statement ok
  404. INSERT INTO t2 VALUES (4, 4), (5, 5), (6, 6), (7, 7), (8, 8);
  405. query RRR
  406. SELECT *
  407. FROM (
  408. SELECT AVG(f1) + 10000 AS agg1
  409. FROM t1
  410. ) a1,
  411. t1 a2
  412. WHERE a2.f2 > a1.agg1;
  413. ----
  414. query RR rowsort
  415. SELECT a2.f2, agg1
  416. FROM (
  417. SELECT AVG(f1) AS agg1 FROM t1
  418. ) a1 ,
  419. t1 a2
  420. WHERE a2.f2 < a1.agg1;
  421. ----
  422. 0.000
  423. 3.900
  424. 1.000
  425. 3.900
  426. 1.000
  427. 3.900
  428. 2.000
  429. 3.900
  430. 2.000
  431. 3.900
  432. 3.000
  433. 3.900
  434. query
  435. SELECT FROM ( SELECT AVG ( f2 ) f2 FROM t2 ) JOIN ( SELECT a2 .f1 FROM t1 JOIN t1 a2 ON TRUE ) ON TRUE WHERE TRUE AND f1 = f2 ;
  436. ----
  437. query B
  438. SELECT a1 .f1 FROM ( SELECT TRUE f1 , MAX ( f1 ) f2 FROM t2 ) a1 RIGHT JOIN ( SELECT f1 FROM t2 ) ON f2 IN ( 1 , f2 ) ;
  439. ----
  440. true
  441. true
  442. true
  443. true
  444. true
  445. true
  446. true
  447. true
  448. true
  449. true
  450. query R
  451. SELECT f1 FROM ( SELECT 2 f1 , MIN ( f2 ) f2 FROM t1 ) a1 RIGHT JOIN ( SELECT f2 FROM t2 ) ON f1 = a1 .f2 ;
  452. ----
  453. NULL
  454. NULL
  455. NULL
  456. NULL
  457. NULL
  458. NULL
  459. NULL
  460. NULL
  461. NULL
  462. NULL
  463. # FilterCharacteristics and IndexedFilter
  464. statement ok
  465. CREATE TABLE big(a int not null, b int not null, c int not null, d int not null, e int not null, f int not null, g int not null, h int not null, i int not null, j int not null, k int not null, x int, y int, s string);
  466. statement ok
  467. CREATE INDEX big_idx_a on big(a);
  468. statement ok
  469. CREATE INDEX big_idx_b on big(b);
  470. statement ok
  471. CREATE INDEX big_idx_c on big(c);
  472. statement ok
  473. CREATE INDEX big_idx_d on big(d);
  474. statement ok
  475. CREATE INDEX big_idx_e on big(e);
  476. statement ok
  477. CREATE INDEX big_idx_f on big(f);
  478. statement ok
  479. CREATE INDEX big_idx_g on big(g);
  480. statement ok
  481. CREATE INDEX big_idx_h on big(h);
  482. statement ok
  483. CREATE INDEX big_idx_i on big(i);
  484. statement ok
  485. CREATE INDEX big_idx_j on big(j);
  486. statement ok
  487. CREATE INDEX big_idx_k on big(k);
  488. statement ok
  489. CREATE INDEX big_idx_y on big(y);
  490. # In the last Delta path (%10):
  491. # - From %9 to %5, there are decreasing FilterCharacteristics.
  492. # - %2 to %4 are all in the any_filter category.
  493. # - %0 and %1 don't have any filters.
  494. query T multiline
  495. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR SELECT * FROM big as t0, big as t1, big as t2, big as t3, big as t4, big as t5, big as t6, big as t7, big as t8, big as t9, big as t10
  496. WHERE
  497. t0.a = t1.b AND
  498. t1.b = t2.c AND
  499. t2.c = t3.d AND
  500. t3.d = t4.e AND
  501. t4.e = t5.f AND
  502. t5.f = t6.g AND
  503. t6.g = t7.h AND
  504. t7.h = t8.i AND
  505. t8.i = t9.j AND
  506. t9.j = t10.k AND
  507. t9.x = 71 AND
  508. t8.s LIKE 'a%' AND
  509. t7.x IS NULL AND
  510. t6.x BETWEEN 3 AND 8 AND
  511. t5.x > 5 AND
  512. t4.s NOT LIKE 'b%' AND
  513. t3.x != t3.y AND
  514. (NOT (t2.x = t2.y))
  515. ;
  516. ----
  517. Explained Query:
  518. Project (#0{a}..=#14{a}, #0{a}, #16{c}..=#29{b}, #0{a}, #31{d}..=#44{c}, #0{a}, #46{e}..=#59{d}, #0{a}, #61{f}..=#74{e}, #0{a}, #76{g}..=#89{f}, #0{a}, #91{h}..=#104{g}, #0{a}, #106{i}..=#119{h}, #0{a}, #121{j}..=#134{i}, #0{a}, #136{k}..=#149{j}, #0{a}, #151{x}..=#153{s}) // { arity: 154 }
  519. Filter (#109{x}) IS NULL AND like["a%"](#125{s}) AND (#137{x} = 71) AND (#95{x} <= 8) AND (#81{x} > 5) AND (#95{x} >= 3) AND NOT(like["b%"](#69{s})) AND (#39{x} != #40{y}) AND (#53{x} != #54{y}) // { arity: 154 }
  520. Join on=(#0{a} = #15{b} = #30{c} = #45{d} = #60{e} = #75{f} = #90{g} = #105{h} = #120{i} = #135{j} = #150{k}) type=delta // { arity: 154 }
  521. implementation
  522. %0:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  523. %1:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %10:big[#10{k}]KA
  524. %2:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  525. %3:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  526. %4:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  527. %5:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  528. %6:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  529. %7:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  530. %8:big » %9:big[#9{j}]KAef » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  531. %9:big » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA » %10:big[#10{k}]KA
  532. %10:big » %9:big[#9{j}]KAef » %8:big[#8{i}]KAlf » %7:big[#7{h}]KAnf » %6:big[#6{g}]KAiif » %5:big[#5{f}]KAif » %2:big[#2{c}]KAf » %3:big[#3{d}]KAf » %4:big[#4{e}]KAf » %0:big[#0{a}]KA » %1:big[#1{b}]KA
  533. ArrangeBy keys=[[#0{a}]] // { arity: 14 }
  534. ReadIndex on=big big_idx_a=[delta join 1st input (full scan)] // { arity: 14 }
  535. ArrangeBy keys=[[#1{b}]] // { arity: 14 }
  536. ReadIndex on=big big_idx_b=[delta join lookup] // { arity: 14 }
  537. ArrangeBy keys=[[#2{c}]] // { arity: 14 }
  538. ReadIndex on=big big_idx_c=[delta join lookup] // { arity: 14 }
  539. ArrangeBy keys=[[#3{d}]] // { arity: 14 }
  540. ReadIndex on=big big_idx_d=[delta join lookup] // { arity: 14 }
  541. ArrangeBy keys=[[#4{e}]] // { arity: 14 }
  542. ReadIndex on=big big_idx_e=[delta join lookup] // { arity: 14 }
  543. ArrangeBy keys=[[#5{f}]] // { arity: 14 }
  544. ReadIndex on=big big_idx_f=[delta join lookup] // { arity: 14 }
  545. ArrangeBy keys=[[#6{g}]] // { arity: 14 }
  546. ReadIndex on=big big_idx_g=[delta join lookup] // { arity: 14 }
  547. ArrangeBy keys=[[#7{h}]] // { arity: 14 }
  548. ReadIndex on=big big_idx_h=[delta join lookup] // { arity: 14 }
  549. ArrangeBy keys=[[#8{i}]] // { arity: 14 }
  550. ReadIndex on=big big_idx_i=[delta join lookup] // { arity: 14 }
  551. ArrangeBy keys=[[#9{j}]] // { arity: 14 }
  552. ReadIndex on=big big_idx_j=[delta join lookup] // { arity: 14 }
  553. ArrangeBy keys=[[#10{k}]] // { arity: 14 }
  554. ReadIndex on=big big_idx_k=[delta join lookup] // { arity: 14 }
  555. Used Indexes:
  556. - materialize.public.big_idx_a (delta join 1st input (full scan))
  557. - materialize.public.big_idx_b (delta join lookup)
  558. - materialize.public.big_idx_c (delta join lookup)
  559. - materialize.public.big_idx_d (delta join lookup)
  560. - materialize.public.big_idx_e (delta join lookup)
  561. - materialize.public.big_idx_f (delta join lookup)
  562. - materialize.public.big_idx_g (delta join lookup)
  563. - materialize.public.big_idx_h (delta join lookup)
  564. - materialize.public.big_idx_i (delta join lookup)
  565. - materialize.public.big_idx_j (delta join lookup)
  566. - materialize.public.big_idx_k (delta join lookup)
  567. Target cluster: quickstart
  568. EOF
  569. # IndexedFilter should
  570. # - come before like (i.e., same category as literal_equality)
  571. # - not prevent planning a Delta join
  572. query T multiline
  573. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR SELECT * FROM big as t0, big as t1, big as t2
  574. WHERE
  575. t0.a = t1.b AND
  576. t1.b = t2.c AND
  577. t1.y = 42 AND
  578. t0.s LIKE 'a%'
  579. ;
  580. ----
  581. Explained Query:
  582. Project (#0{a}..=#14{a}, #0{a}, #16{c}..=#27{s}, #29{a}, #30{b}, #0{a}, #32{d}..=#42{s}) // { arity: 42 }
  583. Filter like["a%"](#13{s}) // { arity: 43 }
  584. Join on=(#0{a} = #15{b} = #31{c}) type=delta // { arity: 43 }
  585. implementation
  586. %0:big » %1:big[#1{b}]KAe » %2:big[#2{c}]KA
  587. %1:big » %0:big[#0{a}]KAlf » %2:big[#2{c}]KA
  588. %2:big » %1:big[#1{b}]KAe » %0:big[#0{a}]KAlf
  589. ArrangeBy keys=[[#0{a}]] // { arity: 14 }
  590. ReadIndex on=big big_idx_a=[delta join 1st input (full scan)] // { arity: 14 }
  591. ArrangeBy keys=[[#1{b}]] // { arity: 15 }
  592. ReadIndex on=materialize.public.big big_idx_y=[lookup value=(42)] // { arity: 15 }
  593. ArrangeBy keys=[[#2{c}]] // { arity: 14 }
  594. ReadIndex on=big big_idx_c=[delta join lookup] // { arity: 14 }
  595. Used Indexes:
  596. - materialize.public.big_idx_a (delta join 1st input (full scan))
  597. - materialize.public.big_idx_c (delta join lookup)
  598. - materialize.public.big_idx_y (lookup)
  599. Target cluster: quickstart
  600. EOF
  601. # FilterCharacteristics from behind a Get. %2 should come at the first or second position in every Delta path,
  602. # and %2 should have an "e", indicating the join ordering code's awareness of the equality filter.
  603. # The magic that makes this work is as follows:
  604. # - inline_mfp has to be true on the last RelationCSE call before JoinImplementation (i.e., in logical_cleanup_pass);
  605. # - There shouldn't be a RelationCSE between the CanonicalizeMfp that is before JoinImplementation and JoinImplementation.
  606. query T multiline
  607. EXPLAIN OPTIMIZED PLAN WITH(humanized expressions, arity, join implementations) AS VERBOSE TEXT FOR
  608. WITH t(x) AS (
  609. SELECT a
  610. FROM big
  611. WHERE a = 5
  612. )
  613. (
  614. SELECT b1.a
  615. FROM big as b1, big as b2, t
  616. )
  617. UNION ALL
  618. (SELECT * FROM t);
  619. ----
  620. Explained Query:
  621. With
  622. cte l0 =
  623. Project (#0{a}) // { arity: 1 }
  624. ReadIndex on=materialize.public.big big_idx_a=[lookup value=(5)] // { arity: 15 }
  625. Return // { arity: 1 }
  626. Union // { arity: 1 }
  627. CrossJoin type=delta // { arity: 1 }
  628. implementation
  629. %0:big » %2:l0[×]e » %1:big[×]
  630. %1:big » %2:l0[×]e » %0:big[×]
  631. %2:l0 » %0:big[×] » %1:big[×]
  632. ArrangeBy keys=[[]] // { arity: 1 }
  633. Project (#0{a}) // { arity: 1 }
  634. ReadIndex on=big big_idx_a=[*** full scan ***] // { arity: 14 }
  635. ArrangeBy keys=[[]] // { arity: 0 }
  636. Project () // { arity: 0 }
  637. ReadIndex on=big big_idx_a=[*** full scan ***] // { arity: 14 }
  638. ArrangeBy keys=[[]] // { arity: 0 }
  639. Project () // { arity: 0 }
  640. Get l0 // { arity: 1 }
  641. Get l0 // { arity: 1 }
  642. Used Indexes:
  643. - materialize.public.big_idx_a (*** full scan ***, lookup)
  644. Target cluster: quickstart
  645. EOF