Re: On function names and such like

Michael Kay <mike@saxonica.com> writes:
> I've certainly been wondering about doing that for a new set of
> collection-oriented functions that treat arrays and sequences
> uniformly.
>
> But it breaks down because the data models for arrays and sequences
> have a fundamental difference.

Well, just to beat this dead horse for a moment or two longer, it seems
to me that a new set of functions can (in principle, at least) tackle
some of these problems in the semantics of the function(s).

For functions that take a sequence and might return a sequence, you
could say:

* If the sequence contains only atomic values, the function operates on
  that sequence and returns a sequence.

* If the sequence contains only arrays, the function operates on the
  (wholly flattend) members of the array(s) and returns an array.

* If the sequence contains only maps, the function operates on the
  key/value pairs in the map(s) and returns a map.

* If the sequence contains a mixture of arrays and atomic values, the
  arrays are wholly flattened and the function operates on the resulting
  sequence.

* If the sequence (after flattening) contains a mixture of maps and
  anything else, that’s an error.

(I can imagine that some functions might have different rules, I’m just
sketching out an idea.)

Given $even, a function that returns true if its numeric argument is
even,

 gn:filter([1,2,3], $even) returns [2]
 gn:filter((1,2,3), $even) returns 2
 gn:filter(([1,2,3], 4), $even) returns 2, 4
 gn:filter((1, map{"a":1}), $even) raises an error

The $even function isn’t going to like maps, so I won’t try to construct
a useful example, but a different function could return something useful
from a map or a list of maps.

Given gn:sequence() that just unwraps arrays and gn:array() that always
returns an array, a user could arrange to get what they wanted
irrespective of whether the function happened to return a sequence or an
array.

 gn:filter([1,2,3], $even) => gn:array() returns [2]
 gn:filter((1,2,3), $even) => gn:array() returns [2]
 gn:filter(([1,2,3], 4), $even) => gn:array() returns [2, 4]

 gn:filter([1,2,3], $even) => gn:sequence() returns 2
 gn:filter((1,2,3), $even) => gn:sequence() returns 2
 gn:filter(([1,2,3], 4), $even) => gn:sequence() returns (2, 4)

I’m not sure this is a good idea. It seems to me like the type checking
around function arguments and return types is woefully sloppy. As
proposed, you’d end up with a whole lot of functions that take item()*
and return item()* which doesn’t bode well for static analysis or
optimization.

> Let's work within the limitations of what we've got.

Sure. (Pulling his chair’s hat down firmly over his ears) I’m just
trying to motivate some discussion on the list so that we might get past
this issue the *third* time it comes up!

                                        Be seeing you,
                                          norm

--
Norm Tovey-Walsh
Saxonica

Received on Wednesday, 13 December 2023 17:06:07 UTC