diff options
| author | Tom Lane <tgl@sss.pgh.pa.us> | 2003-06-29 00:33:44 +0000 |
|---|---|---|
| committer | Tom Lane <tgl@sss.pgh.pa.us> | 2003-06-29 00:33:44 +0000 |
| commit | bee217924d51af8cf0411167bfc8a7eb55122577 (patch) | |
| tree | ab6d3f311de5fd6b415e0bdf032205ed503ba95c /src/backend/utils | |
| parent | df7618020b3845a51d1ba80cb9abfc6df5dfeaff (diff) | |
| download | postgresql-bee217924d51af8cf0411167bfc8a7eb55122577.tar.gz | |
Support expressions of the form 'scalar op ANY (array)' and
'scalar op ALL (array)', where the operator is applied between the
lefthand scalar and each element of the array. The operator must
yield boolean; the result of the construct is the OR or AND of the
per-element results, respectively.
Original coding by Joe Conway, after an idea of Peter's. Rewritten
by Tom to keep the implementation strictly separate from subqueries.
Diffstat (limited to 'src/backend/utils')
| -rw-r--r-- | src/backend/utils/adt/ruleutils.c | 38 | ||||
| -rw-r--r-- | src/backend/utils/fmgr/fmgr.c | 21 |
2 files changed, 45 insertions, 14 deletions
diff --git a/src/backend/utils/adt/ruleutils.c b/src/backend/utils/adt/ruleutils.c index 27259044c1..63b174a39c 100644 --- a/src/backend/utils/adt/ruleutils.c +++ b/src/backend/utils/adt/ruleutils.c @@ -3,7 +3,7 @@ * back to source text * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/utils/adt/ruleutils.c,v 1.142 2003/06/25 03:56:30 momjian Exp $ + * $Header: /cvsroot/pgsql/src/backend/utils/adt/ruleutils.c,v 1.143 2003/06/29 00:33:44 tgl Exp $ * * This software is copyrighted by Jan Wieck - Hamburg. * @@ -2292,19 +2292,33 @@ get_rule_expr(Node *node, deparse_context *context, { DistinctExpr *expr = (DistinctExpr *) node; List *args = expr->args; + Node *arg1 = (Node *) lfirst(args); + Node *arg2 = (Node *) lsecond(args); - Assert(length(args) == 2); - { - /* binary operator */ - Node *arg1 = (Node *) lfirst(args); - Node *arg2 = (Node *) lsecond(args); + appendStringInfoChar(buf, '('); + get_rule_expr(arg1, context, true); + appendStringInfo(buf, " IS DISTINCT FROM "); + get_rule_expr(arg2, context, true); + appendStringInfoChar(buf, ')'); + } + break; - appendStringInfoChar(buf, '('); - get_rule_expr(arg1, context, true); - appendStringInfo(buf, " IS DISTINCT FROM "); - get_rule_expr(arg2, context, true); - appendStringInfoChar(buf, ')'); - } + case T_ScalarArrayOpExpr: + { + ScalarArrayOpExpr *expr = (ScalarArrayOpExpr *) node; + List *args = expr->args; + Node *arg1 = (Node *) lfirst(args); + Node *arg2 = (Node *) lsecond(args); + + appendStringInfoChar(buf, '('); + get_rule_expr(arg1, context, true); + appendStringInfo(buf, " %s %s (", + generate_operator_name(expr->opno, + exprType(arg1), + get_element_type(exprType(arg2))), + expr->useOr ? "ANY" : "ALL"); + get_rule_expr(arg2, context, true); + appendStringInfo(buf, "))"); } break; diff --git a/src/backend/utils/fmgr/fmgr.c b/src/backend/utils/fmgr/fmgr.c index e161bd1e59..0d69ac1083 100644 --- a/src/backend/utils/fmgr/fmgr.c +++ b/src/backend/utils/fmgr/fmgr.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/utils/fmgr/fmgr.c,v 1.70 2003/06/25 21:30:32 momjian Exp $ + * $Header: /cvsroot/pgsql/src/backend/utils/fmgr/fmgr.c,v 1.71 2003/06/29 00:33:44 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -1651,6 +1651,7 @@ get_fn_expr_argtype(FunctionCallInfo fcinfo, int argnum) { Node *expr; List *args; + Oid argtype; /* * can't return anything useful if we have no FmgrInfo or if @@ -1665,11 +1666,27 @@ get_fn_expr_argtype(FunctionCallInfo fcinfo, int argnum) args = ((FuncExpr *) expr)->args; else if (IsA(expr, OpExpr)) args = ((OpExpr *) expr)->args; + else if (IsA(expr, DistinctExpr)) + args = ((DistinctExpr *) expr)->args; + else if (IsA(expr, ScalarArrayOpExpr)) + args = ((ScalarArrayOpExpr *) expr)->args; + else if (IsA(expr, NullIfExpr)) + args = ((NullIfExpr *) expr)->args; else return InvalidOid; if (argnum < 0 || argnum >= length(args)) return InvalidOid; - return exprType((Node *) nth(argnum, args)); + argtype = exprType((Node *) nth(argnum, args)); + + /* + * special hack for ScalarArrayOpExpr: what the underlying function + * will actually get passed is the element type of the array. + */ + if (IsA(expr, ScalarArrayOpExpr) && + argnum == 1) + argtype = get_element_type(argtype); + + return argtype; } |
