Larry Wall wrote:
: * In item context, a list of captures becomes a single Array object,
: and the question about whether or not it gets flattened gets deferred
: until its contents get looked at in list, slice, or hash context.
That's the intent. $() used to assume @@ inside till this latest
change, but that seemed insufficiently lazy to me...
But it kinda means there's yet another list context that doesn't
decide yet, used explicitly by the insides of \(...) and implicitly
by the $() context. Not sure if it needs a name yet, or whether it's
a design smell.
IMHO, no name is needed; just note that \(...) generates a variation
of the list context that is agnostic to flattening, but is otherwise
equivalent to "list".
Arguably "list" should be non-committal and we give
@() a different name like "flat", but that grates in my brain for
some reason, if only because most list contexts would in the end
be flat anyway. And "list" in English already implies something
flatter than, say, an "outline".
...which tends to be more akin to "slice". In fact, consider renaming
"slice" as "outline". Sure, it's two characters longer; but it's
_much_ more descriptive of what's going on. "Slice" strikes me as
something of a holdover from its origins in array indices.
Conversely, our agnostic list _is_ flatter than a slice or outline,
just like a hardcore list is flatter than an agnostic list. I'd tend
to agree about keeping "list" tied to the flattened stuff. IMHO,
you're not going to find anything in English to represent the agnostic
"list of captures".
In essence, we have: list, list-of-captures, and slice (or outline?);
also, hash and item.
: Meanwhile, 'zip' produces a list of captures - which, because list
: context is the default "plural" context, immediately gets flattened
: most of the time. As I see it, then, the serial equivalent to
: 'zip(@a;@b)' would be '(@a;@b)', and 'list(@a;@b)' would be the serial
: equivalent to 'list(zip(@a;@b))'.
That doesn't make sense to me. You seem to be thinking that semicolon
has zip semantics, when it doesn't. All ; does is make a list of
My focus in this comparison is on what is being produced, rather than
on what is being passed in.
My understanding is that 'zip' produces a list of captures. It's just
that the default context that zip is likely to work in is list
context, which flattens that list of captures. Or am I wrong about
this? The other alternative is that zip knows whether it's being
called in list or slice/outline context, and produces its output
accordingly. I was assuming that zip wouldn't need to know; but I
could be wrong about this.
If zip _does_ tailor its return value according to the variety of list
context that it finds itself in, then 'list()' is _still_ not the
serial analog to 'zip()', any more than 'slice()' is, since both
impose a specific context on the product. You'd need a new function
that takes a list of captures as its parameters, and produces a flat
list in list context or a slice or outline in slice/outline context.
: Or does '(@a;@b)' default to slice context?
Parentheses don't supply context. They only group. (@a;@b) returns
a list of captures. It requires a binding (or other sigil) coercion
to supply context.
The parentheses weren't concerning me here; the semicolon within
brackets was. I've been working under the assumption that a bracketed
@a;@b produces an agnostic "list of captures", which then gets
flattened or structured when it hits list or slice context,
respectively; I was asking about the possibility that I was wrong
about this, and that bracket-within-semicolons produces a
This does bring up another question, though: when are you in list
context, and when are you in list-of-captures context? That is, when
do you force a list of captures to flatten, and when do you leave it
Jonathan "Dataweaver" Lang