Thread: variadic flag doesn't work with "any" type
Hello There is missing expansion for variadic parameter from any array to real parameters when variadic type is "any". It can be solved on C level, but in this moment we have not a access to parser, so we don't know, if variadic flag was used or not. Regards Pavel Stehule
Pavel Stehule <pavel.stehule@gmail.com> writes: > There is missing expansion for variadic parameter from any array to > real parameters when variadic type is "any". That's not a bug, it's intentional. Variadic any is intended to let the C function accept any old parameter list. We should not assume that we should do something special with a parameter that happens to be an array. Possibly variadic anyarray will do what you are after. regards, tom lane
2010/12/9 Tom Lane <tgl@sss.pgh.pa.us>: > Pavel Stehule <pavel.stehule@gmail.com> writes: >> There is missing expansion for variadic parameter from any array to >> real parameters when variadic type is "any". > > That's not a bug, it's intentional. =C2=A0Variadic any is intended to let= the > C function accept any old parameter list. =C2=A0We should not assume that= we > should do something special with a parameter that happens to be an array. > > Possibly variadic anyarray will do what you are after. I didn't explain it well, sorry so I have a function foo(variadic "any") usual calling like foo(10,20) or foo('a',10) working perfectly. But I have a problem with call with VARIADIC keyword like foo(VARIADIC ARRAY[10,20]) or foo(VARIADIC ARRAY['a','10']). Keyword VARIADIC is allowed, and this a calling doesn't raise any error. But there isn't transformation to standard parameters. It's in negation to other than "any" types. And because parser doesn't expand array to parameters and just ignore VARIADIC keyword I am must not fix it inside custom function. so: FUNCTION foo(VARIADIC text[]) -------- CALL foo(10,20,20) ---> real call foo(ARRAY['10','20','20']); -------- CALL foo (VARIADIC ARRAY['10','20','20']) ---> real call foo(ARRAY['10','20','20']) -- same mechanism should be for "any" type - in reverse order FUNCTION foo(VARIADIC "any") -------- CALL foo(10,20,20) ---> real call foo(10,20,20); -------- CALL foo(VARIADIC ARRAY[10,20,20]) ---> real call foo(10,20,20) -- but it doesn't work now. Pavel > > =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0regards, tom lane >
Pavel Stehule <pavel.stehule@gmail.com> writes: > I didn't explain it well, sorry > so I have a function foo(variadic "any") > usual calling like foo(10,20) or foo('a',10) working perfectly. But I > have a problem with call with VARIADIC keyword > like foo(VARIADIC ARRAY[10,20]) or foo(VARIADIC ARRAY['a','10']). > Keyword VARIADIC is allowed, and this a calling doesn't raise any > error. What exactly is the use-case for that? You can't expect that an array will hold the parameter list, since the parameters might not be all the same type. > -------- CALL foo(VARIADIC ARRAY[10,20,20]) ---> real > call foo(10,20,20) -- but it doesn't work now. I'm not convinced it should work that way. Even if you had convinced me that this was sensible and had a real use-case, making it work like that would take a whole bunch of mechanism that doesn't exist. regards, tom lane
2010/12/9 Tom Lane <tgl@sss.pgh.pa.us>: > Pavel Stehule <pavel.stehule@gmail.com> writes: >> I didn't explain it well, sorry > >> so I have a function foo(variadic "any") > >> usual calling like foo(10,20) or foo('a',10) working perfectly. But I >> have a problem with call with VARIADIC keyword > >> like foo(VARIADIC ARRAY[10,20]) or foo(VARIADIC ARRAY['a','10']). > >> Keyword VARIADIC is allowed, and this a calling doesn't raise any >> error. > > What exactly is the use-case for that? You can't expect that an array > will hold the parameter list, since the parameters might not be all the > same type. > I am working on function that can help with record updating. It's based on polymorphic types. I would to allow a multiple modification per one call - like UPDATE statement does. some like: record_set_fields(anyelement, key text, value "any" [, key text, value "any" [..]]) returns anyelement because we cannot work with pairs of params I designed interface CREATE FUNCTION record_set_fields(anyelement, VARIADIC "any") RETURNS anyelement most often case working well: SELECT record_set_fields(row(0,0,0,0,0,0), 'f1', 10, 'f2', 20, 'f3', 30) I prefer "any" type because a user must not use a quotes for values - and I am able to do late conversion based on record tuple desc. But sometimes can be interesting to use a VARIADIC value - so list of pairs (key, value) can be created dynamically - (now I don't talk if this is good way or not). And because we have a VARIADIC value for VARIADIC parameter, it should be no problem - It works for non "any" types now. I would to do some like: DECLARE change_set text[]; BEGIN change_set = ARRAY(SELECT CASE WHEN i % 2 = 1 THEN 'f' || (i / 2) ELSE (-100)::text END FROM generate_series(1,10) g(i)); -- change_set = {f0,-100,f1,-100,f2,-100,f3,-100,f4,-100} NEW := record_set_fields(NEW, VARIADIC change_set); ... RETURN NEW; but NEW := record_set_fields(NEW, VARIADIC change_set) doesn't work now - because keyword VARIADIC hasn't necessary effect for "any" type. It's just quietly ignored. Isn't a problem to expand array inside custom function - but I don't have a info if VARIADIC keyword was used or not. From some custom function's perspective there isn't difference between (when "any" type is used): SELECT foo(VARIADIC arrayval) and SELECT foo(arrayval). I don't know when I have to raise exception and when I have to expand array. Regards Pavel p.s. I found a workaroud - but it's a workaround and needs twice code. I have to define second record_set_fields(anyelement, VARIADIC anyarray), and this variant is chosen when VARIADIC value is used. But I afraid about stability of this solution. >> -------- CALL foo(VARIADIC ARRAY[10,20,20]) ---> real >> call foo(10,20,20) -- but it doesn't work now. > > I'm not convinced it should work that way. Even if you had convinced me > that this was sensible and had a real use-case, making it work like that > would take a whole bunch of mechanism that doesn't exist. > > regards, tom lane >
Attachment
Pavel Stehule <pavel.stehule@gmail.com> writes: > 2010/12/9 Tom Lane <tgl@sss.pgh.pa.us>: >> What exactly is the use-case for that? > I am working on function that can help with record updating. It's > based on polymorphic types. I would to allow a multiple modification > per one call - like UPDATE statement does. > some like: > record_set_fields(anyelement, key text, value "any" [, key text, value > "any" [..]]) returns anyelement OK, makes sense, since you don't want to constrain the values to be all the same datatype. > sometimes can be interesting to use a VARIADIC value - so list of > pairs (key, value) can be created dynamically - (now I don't talk if > this is good way or not). That can't work unless you constrain all the values to be text (to match the column-name parameters), which more or less defeats the entire point of the function. So I see no interesting use-case for VARIADIC here. regards, tom lane
2010/12/10 Tom Lane <tgl@sss.pgh.pa.us>: > Pavel Stehule <pavel.stehule@gmail.com> writes: >> 2010/12/9 Tom Lane <tgl@sss.pgh.pa.us>: >>> What exactly is the use-case for that? > >> I am working on function that can help with record updating. It's >> based on polymorphic types. I would to allow a multiple modification >> per one call - like UPDATE statement does. >> some like: >> record_set_fields(anyelement, key text, value "any" [, key text, value >> "any" [..]]) returns anyelement > > OK, makes sense, since you don't want to constrain the values to be all > the same datatype. ok, can I send a patch? Pavel > >> sometimes can be interesting to use a VARIADIC value - so list of >> pairs (key, =C2=A0value) can be created dynamically - (now I don't talk = if >> this is good way or not). > > That can't work unless you constrain all the values to be text (to match > the column-name parameters), which more or less defeats the entire point > of the function. =C2=A0So I see no interesting use-case for VARIADIC here. > > =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0regards, tom lane >
On Fri, Dec 10, 2010 at 2:44 PM, Pavel Stehule <pavel.stehule@gmail.com> wrote: > 2010/12/10 Tom Lane <tgl@sss.pgh.pa.us>: >> Pavel Stehule <pavel.stehule@gmail.com> writes: >>> 2010/12/9 Tom Lane <tgl@sss.pgh.pa.us>: >>>> What exactly is the use-case for that? >> >>> I am working on function that can help with record updating. It's >>> based on polymorphic types. I would to allow a multiple modification >>> per one call - like UPDATE statement does. >>> some like: >>> record_set_fields(anyelement, key text, value "any" [, key text, value >>> "any" [..]]) returns anyelement >> >> OK, makes sense, since you don't want to constrain the values to be all >> the same datatype. > > ok, can I send a patch? In the part of Tom's email you didn't quote, he wrote "this can't work". Did you miss that part? -- Robert Haas EnterpriseDB: http://www.enterprisedb.com The Enterprise PostgreSQL Company