mirror of
https://github.com/postgres/postgres.git
synced 2025-06-26 12:21:12 +03:00
Allow omitting one or both boundaries in an array slice specifier.
Omitted boundaries represent the upper or lower limit of the corresponding
array subscript. This allows simpler specification of many common
use-cases.
(Revised version of commit 9246af6799
)
YUriy Zhuravlev
This commit is contained in:
@ -271,6 +271,8 @@ ExecEvalArrayRef(ArrayRefExprState *astate,
|
||||
j = 0;
|
||||
IntArray upper,
|
||||
lower;
|
||||
bool upperProvided[MAXDIM],
|
||||
lowerProvided[MAXDIM];
|
||||
int *lIndex;
|
||||
|
||||
array_source = ExecEvalExpr(astate->refexpr,
|
||||
@ -300,6 +302,15 @@ ExecEvalArrayRef(ArrayRefExprState *astate,
|
||||
errmsg("number of array dimensions (%d) exceeds the maximum allowed (%d)",
|
||||
i + 1, MAXDIM)));
|
||||
|
||||
if (eltstate == NULL)
|
||||
{
|
||||
/* Slice bound is omitted, so use array's upper bound */
|
||||
Assert(astate->reflowerindexpr != NIL);
|
||||
upperProvided[i++] = false;
|
||||
continue;
|
||||
}
|
||||
upperProvided[i] = true;
|
||||
|
||||
upper.indx[i++] = DatumGetInt32(ExecEvalExpr(eltstate,
|
||||
econtext,
|
||||
&eisnull,
|
||||
@ -328,6 +339,14 @@ ExecEvalArrayRef(ArrayRefExprState *astate,
|
||||
errmsg("number of array dimensions (%d) exceeds the maximum allowed (%d)",
|
||||
j + 1, MAXDIM)));
|
||||
|
||||
if (eltstate == NULL)
|
||||
{
|
||||
/* Slice bound is omitted, so use array's lower bound */
|
||||
lowerProvided[j++] = false;
|
||||
continue;
|
||||
}
|
||||
lowerProvided[j] = true;
|
||||
|
||||
lower.indx[j++] = DatumGetInt32(ExecEvalExpr(eltstate,
|
||||
econtext,
|
||||
&eisnull,
|
||||
@ -398,6 +417,7 @@ ExecEvalArrayRef(ArrayRefExprState *astate,
|
||||
econtext->caseValue_datum =
|
||||
array_get_slice(array_source, i,
|
||||
upper.indx, lower.indx,
|
||||
upperProvided, lowerProvided,
|
||||
astate->refattrlength,
|
||||
astate->refelemlength,
|
||||
astate->refelembyval,
|
||||
@ -456,6 +476,7 @@ ExecEvalArrayRef(ArrayRefExprState *astate,
|
||||
else
|
||||
return array_set_slice(array_source, i,
|
||||
upper.indx, lower.indx,
|
||||
upperProvided, lowerProvided,
|
||||
sourceData,
|
||||
eisnull,
|
||||
astate->refattrlength,
|
||||
@ -475,6 +496,7 @@ ExecEvalArrayRef(ArrayRefExprState *astate,
|
||||
else
|
||||
return array_get_slice(array_source, i,
|
||||
upper.indx, lower.indx,
|
||||
upperProvided, lowerProvided,
|
||||
astate->refattrlength,
|
||||
astate->refelemlength,
|
||||
astate->refelembyval,
|
||||
|
Reference in New Issue
Block a user