Re: .map/.reduce with larger arity

2009-03-25 Thread Moritz Lenz
Leon Timmermans wrote:

> I would propose there to be one difference between for an map: map
> should bind its arguments read-only, for should bind them read-write.
> That would make at least one bad practice an error.

That sounds very impractical, because the ro/rw distinction is part of
the signature, not of the capture.

Cheers,
Moritz


Re: .map/.reduce with larger arity

2009-03-25 Thread Moritz Lenz
Leon Timmermans wrote:

> I would propose there to be one difference between for an map: map
> should bind its arguments read-only, for should bind them read-write.
> That would make at least one bad practice an error.

That sounds very impractical, because the ro/rw distinction is part of
the signature, not of the capture.

Cheers,
Moritz


Re: .map/.reduce with larger arity

2009-03-25 Thread Mark J. Reed
On Wed, Mar 25, 2009 at 6:20 PM, Leon Timmermans  wrote:
> I would propose there to be one difference between for an map: map
> should bind its arguments read-only, for should bind them read-write.
> That would make at least one bad practice an error.

Why is r/w map a bad practice if r/w for is not?

Do you look at Perl's "map" and think "A-ha!  The map operation is a
functional programming idiom, therefore it must be side-effect free!"?
 Because that view doesn't feel terribly Perlish to me.

While I mostly use both map and for in readonly mode, I've been known
to use map for quickie in place mutations, and not necessarily in void
context:

my @prev = map { $_++ } @values;

I'm not arguing for the binding to default to rw - you can always use
"is rw" when needed.  I just don't see any reason why the default
binding behavior of map and for should be different.

-- 
Mark J. Reed 


Re: .map/.reduce with larger arity

2009-03-25 Thread Leon Timmermans
On Tue, Mar 10, 2009 at 12:09 AM, Larry Wall  wrote:
>
> Yes, the only difference between C and C is that you can
> only use C at the start of a statement.  But we're more liberal
> about where statements are expected in Perl 6, so you can say things
> like:
>
>    my @results = do for @list -> $x {...};
>    my @results = (for @list -> $x {...});
>
> and either of those is equivalent to:
>
>    my @results = map -> $x {...}, @list;
>
> I also Officially Don't Care if you use map in a void context. :)
>
> Larry
>

I would propose there to be one difference between for an map: map
should bind its arguments read-only, for should bind them read-write.
That would make at least one bad practice an error.

Leon


Re: .map/.reduce with larger arity

2009-03-10 Thread Daniel Ruoso
Em Seg, 2009-03-09 às 12:24 -0700, Larry Wall escreveu:
> On Mon, Mar 09, 2009 at 02:40:43PM -0300, Daniel Ruoso wrote:
> :   ... $capture ~~ $signature ...;
> :   my $args_matched = @($/).elems;
> :   &code.(|$/);
> That API still would not tell the match whether signature must match the
> entire capture (what you want for normal binding) or can stop part way
> (what you want for map and friends).

if $capture ~~ $signature :partial {
  $capture = $;
  &code.(|@($/));
}

daniel



Re: .map/.reduce with larger arity

2009-03-10 Thread Larry Wall
On Tue, Mar 10, 2009 at 07:46:51PM +1300, Martin D Kealey wrote:
: I'd like to be able to use grep, map, etc in a currying fashion. Can I do:
: 
:   my &square_list := -> $x { $x * $x }.map();

my &square_list := &map.assuming(-> $x { $x * $x});

: And if so, what is the signature of &square_list ?

Just (*...@list) or some such.

Larry


Re: .map/.reduce with larger arity

2009-03-09 Thread Martin D Kealey
On Mon, 9 Mar 2009, Larry Wall wrote:

> the only difference between C and C is that you can only use
> C at the start of a statement.  But we're more liberal about where
> statements are expected in Perl 6, so you can say things like:
>
> my @results = do for @list -> $x {...};
> my @results = (for @list -> $x {...});
>
> and either of those is equivalent to:
>
> my @results = map -> $x {...}, @list;
>
> I also Officially Don't Care if you use map in a void context. :)

(Good.)

 Maybe we should just treat "map" as a synonym for "for". 


I'd like to be able to use grep, map, etc in a currying fashion. Can I do:

my &square_list := -> $x { $x * $x }.map();

And if so, what is the signature of &square_list ?

Maybe that's why there's a difference between "for" and "map"

@list = @array.map(&code);

&iterator = &code.for($signature);
@list = iterator(@list);

But I suspect they should logically be the other way around:

&iterator = &code.map($signature);
@list = iterator(@list);

@list = @array.for(&code);

-Martin


Re: .map/.reduce with larger arity

2009-03-09 Thread Larry Wall
On Mon, Mar 09, 2009 at 11:38:29AM -0500, Patrick R. Michaud wrote:
: On Sun, Mar 08, 2009 at 09:31:19PM -0700, Larry Wall wrote:
: > On Sun, Mar 08, 2009 at 09:36:17PM +0100, Moritz Lenz wrote:
: > : But both pugs and rakudo respect the arity of the code ref passed to it,
: > : so that (1..6).map({$^a + $^b + $^c}) returns the list (6, 15), which is
: > : very nice and very DWIM'my.
: > : 
: > : But it opens the question what should happen if there is a number of
: > : items in the list that's not easily divisible by the arity - should the
: > : rest just be padded with undef's? or just ignored? Or fail() with a
: > : friendly error message?
: > 
: > I think the basic rule has to be simply can the signature bind to
: > the remaining arguments.  If not, we get a warning on unused arguments.
: > We can mark arguments as optional if that's what we mean.  
: > [...]
: > My gut feeling is that
: > placeholder variables probably should not be considered optional; in
: > most cases a non-divisible number of arguments indicates a logic error
: > in the program, and an earlier message is better, even at the expense
: > of thowing away some (possibly valid) partial data.  Especially since
: > we do have a way to indicate that partial data is acceptable:
: > 
: > -> $a, $b?, $c? { $a + ($b//0) + ($c//0) }
: 
: Presumably whatever we decide for C also applies to C, yes?
: 
: for 1..4 -> $a, $b, $c { ... }  # error
: for 1..4 -> $a, $b, $c? { ... } # error
: for 1..4 -> $a, $b?, $c? { ... }# ok

Yes, the only difference between C and C is that you can
only use C at the start of a statement.  But we're more liberal
about where statements are expected in Perl 6, so you can say things
like:

my @results = do for @list -> $x {...};
my @results = (for @list -> $x {...});

and either of those is equivalent to:

my @results = map -> $x {...}, @list;

I also Officially Don't Care if you use map in a void context. :)

Larry


Re: .map/.reduce with larger arity

2009-03-09 Thread Larry Wall
On Mon, Mar 09, 2009 at 02:40:43PM -0300, Daniel Ruoso wrote:
: Em Dom, 2009-03-08 às 21:31 -0700, Larry Wall escreveu:
: > I think the basic rule has to be simply can the signature bind to
: > the remaining arguments.  If not, we get a warning on unused arguments.
: 
: Just to put here an idea I sent on irc...
: 
: What if Signature.ACCEPTS set $/ with the matched arguments?
: 
: That way we can both know how many arguments the Signature can receive
: as well as allow us to use the match as the capture to that call...
: 
:   ... $capture ~~ $signature ...;
:   my $args_matched = @($/).elems;
:   &code.(|$/);

That API still would not tell the match whether signature must match the
entire capture (what you want for normal binding) or can stop part way
(what you want for map and friends).

Larry


Re: .map/.reduce with larger arity

2009-03-09 Thread Daniel Ruoso
Em Dom, 2009-03-08 às 21:31 -0700, Larry Wall escreveu:
> I think the basic rule has to be simply can the signature bind to
> the remaining arguments.  If not, we get a warning on unused arguments.

Just to put here an idea I sent on irc...

What if Signature.ACCEPTS set $/ with the matched arguments?

That way we can both know how many arguments the Signature can receive
as well as allow us to use the match as the capture to that call...

  ... $capture ~~ $signature ...;
  my $args_matched = @($/).elems;
  &code.(|$/);

daniel



Re: .map/.reduce with larger arity

2009-03-09 Thread Patrick R. Michaud
On Sun, Mar 08, 2009 at 09:31:19PM -0700, Larry Wall wrote:
> On Sun, Mar 08, 2009 at 09:36:17PM +0100, Moritz Lenz wrote:
> : But both pugs and rakudo respect the arity of the code ref passed to it,
> : so that (1..6).map({$^a + $^b + $^c}) returns the list (6, 15), which is
> : very nice and very DWIM'my.
> : 
> : But it opens the question what should happen if there is a number of
> : items in the list that's not easily divisible by the arity - should the
> : rest just be padded with undef's? or just ignored? Or fail() with a
> : friendly error message?
> 
> I think the basic rule has to be simply can the signature bind to
> the remaining arguments.  If not, we get a warning on unused arguments.
> We can mark arguments as optional if that's what we mean.  
> [...]
> My gut feeling is that
> placeholder variables probably should not be considered optional; in
> most cases a non-divisible number of arguments indicates a logic error
> in the program, and an earlier message is better, even at the expense
> of thowing away some (possibly valid) partial data.  Especially since
> we do have a way to indicate that partial data is acceptable:
> 
> -> $a, $b?, $c? { $a + ($b//0) + ($c//0) }

Presumably whatever we decide for C also applies to C, yes?

for 1..4 -> $a, $b, $c { ... }  # error
for 1..4 -> $a, $b, $c? { ... } # error
for 1..4 -> $a, $b?, $c? { ... }# ok

Pm


Re: .map/.reduce with larger arity

2009-03-08 Thread Larry Wall
On Sun, Mar 08, 2009 at 09:36:17PM +0100, Moritz Lenz wrote:
: Currently the spec says:
: 
:  C returns a lazily evaluated list which is comprised of
:  the return value of the expression, evaluated once for every
:  one of the C<@values> that are passed in.
: 
: But both pugs and rakudo respect the arity of the code ref passed to it,
: so that (1..6).map({$^a + $^b + $^c}) returns the list (6, 15), which is
: very nice and very DWIM'my.
: 
: But it opens the question what should happen if there is a number of
: items in the list that's not easily divisible by the arity - should the
: rest just be padded with undef's? or just ignored? Or fail() with a
: friendly error message?
: 
: I don't really mind either way, just want to test and implement it
: correctly.

I think the basic rule has to be simply can the signature bind to
the remaining arguments.  If not, we get a warning on unused arguments.
We can mark arguments as optional if that's what we mean.  About the
only thing I see to decide is whether the 2nd and subsequent placeholders
consider themselves optional parameters.  Is it better to get a single warning
earlier when some arguments go unused, or is it better to assume the
subsequent code can handle undefined paramets, with the likely result
of more undefined access warnings later on?  My gut feeling is that
placeholder variables probably should not be considered optional; in
most cases a non-divisible number of arguments indicates a logic error
in the program, and an earlier message is better, even at the expense
of thowing away some (possibly valid) partial data.  Especially since
we do have a way to indicate that partial data is acceptable:

-> $a, $b?, $c? { $a + ($b//0) + ($c//0) }

Larry