1#include "duckdb/common/helper.hpp"
2#include "expression_helper.hpp"
3#include "duckdb/optimizer/rule/distributivity.hpp"
4
5using namespace duckdb;
6using namespace std;
7
8TEST_CASE("Distributivity test", "[optimizer]") {
9 ExpressionHelper helper;
10
11 REQUIRE(helper.AddColumns("A BOOLEAN, B BOOLEAN, C BOOLEAN, D BOOLEAN, X BOOLEAN, Y BOOLEAN, Z BOOLEAN").empty());
12 helper.AddRule<DistributivityRule>();
13
14 string input, expected_output;
15
16 // "(NULL AND FALSE) OR (NULL AND TRUE)"
17 // "NULL AND (FALSE OR TRUE)"
18
19 input = "(X AND A AND B) OR (A AND X AND C) OR (X AND B AND D)";
20 expected_output = "X AND ((A AND B) OR (A AND C) OR (B AND D))";
21 REQUIRE(helper.VerifyRewrite(input, expected_output));
22
23 input = "(X AND B) OR (X AND C)";
24 expected_output = "X AND (B OR C)";
25 REQUIRE(helper.VerifyRewrite(input, expected_output));
26
27 input = "X OR X";
28 expected_output = "X::BOOLEAN";
29 REQUIRE(helper.VerifyRewrite(input, expected_output));
30
31 input = "X OR X OR X OR X";
32 expected_output = "X::BOOLEAN";
33 REQUIRE(helper.VerifyRewrite(input, expected_output));
34
35 input = "X OR (X AND A)";
36 expected_output = "X AND A";
37 REQUIRE(helper.VerifyRewrite(input, expected_output));
38
39 input = "X OR (X OR (X OR X))";
40 expected_output = "X::BOOLEAN";
41 REQUIRE(helper.VerifyRewrite(input, expected_output));
42
43 // This rewrite is possible, but possibly not desirable, as we don't actually push an AND as the root expression
44 // before this rewrite would be performed accidently, now we don't do it anymore, does that matter?
45 // input = "((X AND A) OR (X AND B)) OR ((Y AND C) OR (Y AND D))";
46 // expected_output = "(X AND (A OR B)) OR (Y AND (C OR D))";
47 // REQUIRE(helper.VerifyRewrite(input, expected_output));
48
49 REQUIRE(helper.AddColumns("X INTEGER, Y INTEGER, Z INTEGER").empty());
50 input = "(X=1 AND Y=1) OR (X=1 AND Z=1)";
51 expected_output = "X=1 AND (Y=1 OR Z=1)";
52 REQUIRE(helper.VerifyRewrite(input, expected_output));
53}
54