Skip to content

Commit cb222d4

Browse files
Fix rewriting trigonometric funcs with degrees arg (#57)
Signed-off-by: Ahmet Gedemenli <[email protected]>
1 parent 6019711 commit cb222d4

File tree

2 files changed

+92
-39
lines changed

2 files changed

+92
-39
lines changed

pg_lake_engine/src/pgduck/rewrite_query.c

Lines changed: 53 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -162,6 +162,7 @@ static Node *RewriteFuncExprCardinality(Node *node, void *context);
162162
static Node *RewriteFuncExprArrayLength(Node *node, void *context);
163163
static Node *RewriteFuncExprPostgisBytea(Node *node, void *context);
164164
static Node *RewriteFuncExprTrigonometry(Node *node, void *context);
165+
static Node *RewriteFuncExprInverseTrigonometry(Node *node, void *context);
165166
static Node *RewriteFuncExprJsonbArrayLength(Node *node, void *context);
166167
static Node *RewriteFuncExprEncode(Node *node, void *context);
167168
static Node *RewriteFuncExprDecode(Node *node, void *context);
@@ -258,16 +259,16 @@ static FunctionCallRewriteRuleByName BuiltinFunctionCallRewriteRulesByName[] =
258259

259260
/* degree variants of trigonometry functions */
260261
{
261-
"pg_catalog", "acosd", RewriteFuncExprTrigonometry, 0
262+
"pg_catalog", "acosd", RewriteFuncExprInverseTrigonometry, 0
262263
},
263264
{
264-
"pg_catalog", "asind", RewriteFuncExprTrigonometry, 0
265+
"pg_catalog", "asind", RewriteFuncExprInverseTrigonometry, 0
265266
},
266267
{
267-
"pg_catalog", "atand", RewriteFuncExprTrigonometry, 0
268+
"pg_catalog", "atand", RewriteFuncExprInverseTrigonometry, 0
268269
},
269270
{
270-
"pg_catalog", "atan2d", RewriteFuncExprTrigonometry, 0
271+
"pg_catalog", "atan2d", RewriteFuncExprInverseTrigonometry, 0
271272
},
272273
{
273274
"pg_catalog", "cosd", RewriteFuncExprTrigonometry, 0
@@ -2095,7 +2096,7 @@ RewriteFuncExprCardinality(Node *node, void *context)
20952096

20962097
/*
20972098
* RewriteFuncExprTrigonometry rewrites several trigonometry
2098-
* function calls by adding a degrees(..) call.
2099+
* function calls by adding a radians(..) call.
20992100
*/
21002101
static Node *
21012102
RewriteFuncExprTrigonometry(Node *node, void *context)
@@ -2105,22 +2106,6 @@ RewriteFuncExprTrigonometry(Node *node, void *context)
21052106
/* find the no degrees variant */
21062107
switch (funcExpr->funcid)
21072108
{
2108-
case F_ACOSD:
2109-
funcExpr->funcid = F_ACOS;
2110-
break;
2111-
2112-
case F_ASIND:
2113-
funcExpr->funcid = F_ASIN;
2114-
break;
2115-
2116-
case F_ATAND:
2117-
funcExpr->funcid = F_ATAN;
2118-
break;
2119-
2120-
case F_ATAN2D:
2121-
funcExpr->funcid = F_ATAN2;
2122-
break;
2123-
21242109
case F_COSD:
21252110
funcExpr->funcid = F_COS;
21262111
break;
@@ -2141,6 +2126,53 @@ RewriteFuncExprTrigonometry(Node *node, void *context)
21412126
elog(ERROR, "unexpected function ID in rewrite %d", funcExpr->funcid);
21422127
}
21432128

2129+
FuncExpr *radiansExpr = makeNode(FuncExpr);
2130+
2131+
radiansExpr->funcid = F_RADIANS;
2132+
radiansExpr->funcresulttype = funcExpr->funcresulttype;
2133+
radiansExpr->funcretset = false;
2134+
radiansExpr->funcvariadic = false;
2135+
radiansExpr->funcformat = COERCE_EXPLICIT_CALL;
2136+
radiansExpr->location = -1;
2137+
radiansExpr->args = funcExpr->args;
2138+
2139+
funcExpr->args = list_make1((Node *) radiansExpr);
2140+
return (Node *) funcExpr;
2141+
}
2142+
2143+
2144+
/*
2145+
* RewriteFuncExprInverseTrigonometry rewrites several inverse
2146+
* trigonometry function calls by adding a degrees(..) call.
2147+
*/
2148+
static Node *
2149+
RewriteFuncExprInverseTrigonometry(Node *node, void *context)
2150+
{
2151+
FuncExpr *funcExpr = castNode(FuncExpr, node);
2152+
2153+
/* find the no degrees variant */
2154+
switch (funcExpr->funcid)
2155+
{
2156+
case F_ACOSD:
2157+
funcExpr->funcid = F_ACOS;
2158+
break;
2159+
2160+
case F_ASIND:
2161+
funcExpr->funcid = F_ASIN;
2162+
break;
2163+
2164+
case F_ATAND:
2165+
funcExpr->funcid = F_ATAN;
2166+
break;
2167+
2168+
case F_ATAN2D:
2169+
funcExpr->funcid = F_ATAN2;
2170+
break;
2171+
2172+
default:
2173+
elog(ERROR, "unexpected function ID in rewrite %d", funcExpr->funcid);
2174+
}
2175+
21442176
FuncExpr *degreesExpr = makeNode(FuncExpr);
21452177

21462178
degreesExpr->funcid = F_DEGREES;
@@ -2155,7 +2187,6 @@ RewriteFuncExprTrigonometry(Node *node, void *context)
21552187
}
21562188

21572189

2158-
21592190
/*
21602191
* RewriteFuncExprPostgisBytea rewrites bytea(geometry) function calls into
21612192
* ST_AsWKB(..) function calls to push down (implicit) casts.

pg_lake_table/tests/pytests/test_mathematical_functions_pushdown.py

Lines changed: 39 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -76,53 +76,73 @@
7676
("trunc(double)", "WHERE trunc(col_double) = 1.0", "trunc(", True),
7777
("trunc(numeric)", "WHERE trunc(col_numeric) = 1.0", "trunc(", True),
7878
# Trigonometry operators, input must be in the range [-1,1]
79-
("acos", "WHERE abs(col_double) < 1 and acos(col_double) > 0", "acos(", True),
79+
(
80+
"acos",
81+
"WHERE abs(col_double)<1 and abs(acos(col_double) - 0.988432) < 0.001",
82+
"acos(",
83+
True,
84+
),
8085
(
8186
"acosd",
82-
"WHERE abs(col_double) < 1 and acosd(col_double) > 0",
87+
"WHERE abs(col_double)<1 and abs(acosd(col_double) - 56.63298) < 0.001",
8388
"degrees(acos(",
8489
True,
8590
),
86-
("asin", "WHERE abs(col_double) < 1 and asin(col_double) < 0", "asin(", True),
91+
(
92+
"asin",
93+
"WHERE abs(col_double)<1 and abs(asin(col_double) - 0.582364) < 0.001",
94+
"asin(",
95+
True,
96+
),
8797
(
8898
"asind",
89-
"WHERE abs(col_double) < 1 and asind(col_double) < 0",
99+
"WHERE abs(col_double)<1 and abs(asind(col_double) - 33.36701) < 0.001",
90100
"degrees(asin(",
91101
True,
92102
),
93-
("atan", "WHERE abs(col_double) < 1 and atan(col_double) < 0", "atan(", True),
103+
(
104+
"atan",
105+
"WHERE abs(atan(col_double) - 0.5028432) < 0.001",
106+
"atan(",
107+
True,
108+
),
94109
(
95110
"atand",
96-
"WHERE abs(col_double) < 1 and atand(col_double) < 0",
111+
"WHERE abs(atand(col_double) - 28.81079) < 0.001",
97112
"degrees(atan(",
98113
True,
99114
),
100-
("atan2", "WHERE abs(col_double) < 1 and atan2(col_double, 1) < 0", "atan2(", True),
115+
(
116+
"atan2",
117+
"WHERE abs(atan2(col_double, 1) - 0.5028432) < 0.001",
118+
"atan2(",
119+
True,
120+
),
101121
(
102122
"atan2d",
103-
"WHERE abs(col_double) < 1 and atan2d(col_double, 1) < 0",
123+
"WHERE abs(atan2d(col_double, 1) - 28.810793) < 0.001",
104124
"degrees(atan2(",
105125
True,
106126
),
107-
("cos", "WHERE abs(col_double) < 1 and cos(col_double) > 0", "cos(", True),
127+
("cos", "WHERE abs(cos(col_double) - 0.8525245) < 0.001", "cos(", True),
108128
(
109129
"cosd",
110-
"WHERE abs(col_double) < 1 and cosd(col_double) > 0",
111-
"degrees(cos(",
130+
"WHERE abs(cosd(col_double) - 0.999953) < 0.001",
131+
"cos(radians(",
112132
True,
113133
),
114-
("sin", "WHERE abs(col_double) < 1 and sin(col_double) < 0", "sin(", True),
134+
("sin", "WHERE abs(sin(col_double) - 0.522687) < 0.001", "sin(", True),
115135
(
116136
"sind",
117-
"WHERE abs(col_double) < 1 and sind(col_double) < 0",
118-
"degrees(sin(",
137+
"WHERE abs(sind(col_double) - 0.00959) < 0.001",
138+
"sin(radians(",
119139
True,
120140
),
121-
("tan", "WHERE abs(col_double) < 1 and tan(col_double) < 0", "tan(", True),
141+
("tan", "WHERE abs(tan(col_double) - 0.61310) < 0.001", "tan(", True),
122142
(
123143
"tand",
124-
"WHERE abs(col_double) < 1 and tand(col_double) < 0",
125-
"degrees(tan(",
144+
"WHERE abs(tand(col_double) - 0.00959) < 0.001",
145+
"tan(radians(",
126146
True,
127147
),
128148
]
@@ -166,6 +186,8 @@ def create_math_pushdown_table(pg_conn, s3, extension):
166186
UNION ALL
167187
SELECT -1, -1, -100, -1.1, -0.1, 2.2, 2.2, 2.2
168188
UNION ALL
189+
SELECT -1, -1, -100, -1.1, 0.55, 2.2, 2.2, 2.2
190+
UNION ALL
169191
SELECT 1561, 223123, -100123, -111.111111, -12222.1222222, 21231.2123123, 4534652.2456456, 4.2
170192
) TO '{url}' WITH (FORMAT 'parquet');
171193
""",

0 commit comments

Comments
 (0)