Distributive -> and indirect slices 
Author Message
 Distributive -> and indirect slices

I have an idea that I'm going to try to put into my Perl, but I want some
'professional' opinions on it first.

The first thing I'd like to do, is make the -> operator 'distributive' for
all cases of it (that I can think of anyways).

Examples:

    # Call $x->foo(); and $y->foo(); instead of
    # current, less-useful $y->foo();
    ($x, $y)->foo();


    # current 'Can't call method ... without a package or object
    # reference'

    # Call both functions with args
    ($coderef1, $coderef2)->('Param1', 2);

    # Return (1, 3) in list context as lvalues
    ([1, 2], [3, 4])->[0];

    # Return (1234, 5432) (hash derefs) in list context as lvalues
    ({'key' => 1234}, {'key' => 5432})->{'key'};

This would be different from the standard -> notation in that the left
side of the value is a list or array, instead of a scalar.  This
distinction makes it possible to allow the -> notation to create indirect
slices:


because I can say (hopefully), "If the left side is a list, then the index
is also a list".  This logic would allow things like this:

    ($structure)->[1,3,7]->{'key1', 'key2'}; # Returns 6 things

Or this, to get really nuts:

    # foo() is called in list context...


    $structure[0]->[2]->{'keyA'}->foo();
    $structure[0]->[2]->{'keyB'}->foo();
    $structure[0]->[2]->{'keyC'}->foo();
    $structure[0]->[0]->{'keyA'}->foo();
    $structure[0]->[0]->{'keyB'}->foo();
    $structure[0]->[0]->{'keyC'}->foo();
    $structure[0]->[3]->{'keyA'}->foo();
    $structure[0]->[3]->{'keyB'}->foo();
    $structure[0]->[3]->{'keyC'}->foo();
    $structure[0]->[1]->{'keyA'}->foo();
    $structure[0]->[1]->{'keyB'}->foo();
    $structure[0]->[1]->{'keyC'}->foo();

and returns the return values of foo() as one big long list.

Or this, to use a simple slice on a reference:

    ($arrayref)->[0..15]; # The () gives me list context

Without changing the behaviour of this:

    # Still returns boring old $arrayref->[0]
    $arrayref->[0..15];

or this:

    # Still returns boring old $arrayref->[15]
    $arrayref->[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];

I was looking at perly.y and I was kind of thinking that I would need to
change the various 'term ARROW ...' rules to do some sort of check on the
left-hand side.

Is this worth investigating?  Is there any chance that such behaviour
would ever be integrated into Perl 5?  What about Perl 6?

Thanks for any feedback!

- D




Wed, 03 Sep 2003 06:39:03 GMT  
 Distributive -> and indirect slices

Quote:

> The first thing I'd like to do, is make the -> operator 'distributive' for
> all cases of it (that I can think of anyways).

This is usually handled by some kind of 'map' operator.
('map' in perl, 'mapcar' et al. in lisp...)

Quote:
>     ($x, $y)->foo();

        map { $_->foo() } $x, $y;


Quote:
>     ($coderef1, $coderef2)->('Param1', 2);

        map { $_->('Param1',2) } $cr1, $cr2;

Quote:
>     ([1, 2], [3, 4])->[0];

        map { $_->[0] } [1,2], [3,4];

Quote:
>     ({'key' => 1234}, {'key' => 5432})->{'key'};

        map { $_->{'key'} } {'key' => 1234}, {'key' => 5432};

Quote:
>     ($structure)->[1,3,7]->{'key1', 'key2'}; # Returns 6 things



Quote:
> Or this, to use a simple slice on a reference:
>     ($arrayref)->[0..15]; # The () gives me list context


Quote:
> Is this worth investigating?  Is there any chance that such behaviour
> would ever be integrated into Perl 5?  What about Perl 6?

Perl6 will very likely have much better support for this kind of
Functional Programming, so that you could build an operator such as
you propose yourself.  See RFC 23:

        http://dev.perl.org/rfc/23.html

--
John Porter

Useless use of time in void context.



Fri, 05 Sep 2003 00:36:51 GMT  
 Distributive -> and indirect slices


Quote:
>I have an idea that I'm going to try to put into my Perl, but I want some
>'professional' opinions on it first.

>The first thing I'd like to do, is make the -> operator 'distributive' for
>all cases of it (that I can think of anyways).

>Examples:

>    # Call $x->foo(); and $y->foo(); instead of
>    # current, less-useful $y->foo();
>    ($x, $y)->foo();

In list context, '(expr1, expr2)' has each argument evaluated in list context
and then the results are returned as a list.

In scalar context, '(expr1, expr2)' is two expressions with the comma
operator inbetween them.  It evaluates the first expression, throws the
result away, evaluates the second expresion, and uses its result as the
scalar result.

By the time the -> is processed, expr1 has come and gone.  Gratuitous
changes the definition of the comma operator are not to be taken lightly.
        -Joe
--
See http://www.inwap.com/ for PDP-10 and "ReBoot" pages.



Sat, 06 Sep 2003 04:01:41 GMT  
 Distributive -> and indirect slices

Quote:



> >I have an idea that I'm going to try to put into my Perl, but I want some
> >'professional' opinions on it first.

> >The first thing I'd like to do, is make the -> operator 'distributive' for
> >all cases of it (that I can think of anyways).

> >Examples:

> >    # Call $x->foo(); and $y->foo(); instead of
> >    # current, less-useful $y->foo();
> >    ($x, $y)->foo();

> In list context, '(expr1, expr2)' has each argument evaluated in list context
> and then the results are returned as a list.

> In scalar context, '(expr1, expr2)' is two expressions with the comma
> operator inbetween them.  It evaluates the first expression, throws the
> result away, evaluates the second expresion, and uses its result as the
> scalar result.

> By the time the -> is processed, expr1 has come and gone.  Gratuitous
> changes the definition of the comma operator are not to be taken lightly.

No change to the definition of the comma operator is proposed.  The
proposed change puts the left operand of -> in a list context.

Please see my responses to this proposal in .misc - grrr...

--
     \\   ( )
  .  _\\__[oo

 .  l___\\
  # ll  l\\
 ###LL  LL\\



Sat, 06 Sep 2003 16:18:09 GMT  
 Distributive -> and indirect slices

Quote:

> I have an idea that I'm going to try to put into my Perl, but I want
> some 'professional' opinions on it first.

> The first thing I'd like to do, is make the -> operator 'distributive'
> for all cases of it (that I can think of anyways).

> Examples:

For some of what you want, you'd be best off with map.  For other parts
of what you want, you'd be best off using the following module:

use Quantum::Superpositions;

Quote:
>     # Call $x->foo(); and $y->foo(); instead of
>     # current, less-useful $y->foo();
>     ($x, $y)->foo();

        eigenvalues all($x,$y)->foo();

The function all makes a single scalar with the the values $x and $y
superimposed.  Calling foo on that scalar creates a single scalar with
the values of $x->foo and $y->foo superimposed.  eigenvalues
un-superimposes them, resulting in a list.  The above is the same as
doing this:

        map $_->foo(), $x, $y;

You can leave out the eigenvalues, if you aren't planning on using the
return value.  Of course, if you aren't planning on using the result,
then why aren't you doing:


?

Quote:

>     # current 'Can't call method ... without a package or object
>     # reference'



Quote:
>     # Call both functions with args
>     ($coderef1, $coderef2)->('Param1', 2);

        eigenvalues all($coderef1, $coderef2)->('Param1', 2);

Quote:

>     # Return (1, 3) in list context as lvalues
>     ([1, 2], [3, 4])->[0];

        eigenvalues all( [1,2], [3,4] )->[0];

Quote:
>     # Return (1234, 5432) (hash derefs) in list context as lvalues
>     ({'key' => 1234}, {'key' => 5432})->{'key'};

        eigenvalues all({'key' => 1234}, {'key' => 5432})->{'key'};

Again, this might not be implemented yet.

Quote:
> This would be different from the standard -> notation in that the left
> side of the value is a list or array, instead of a scalar.  This
> distinction makes it possible to allow the -> notation to create
> indirect slices:



What do you expect this to return?  A flat list of the slices from each
ref, or a ref to a slice of each ref?

For the latter, you'd be better off doing:


Quote:
> because I can say (hopefully), "If the left side is a list, then the
> index is also a list".  This logic would allow things like this:

>     ($structure)->[1,3,7]->{'key1', 'key2'}; # Returns 6 things




Quote:
> Or this, to get really nuts:

>     # foo() is called in list context...


        Well:


        $aslice = $struct->[all(2,0,3,1)];
        $hslice = $aslice->{all(qw(keyA keyB keyC))};
        $fooval = $hslice->foo;

This can be used as is.  Suppose if you want to test that all the
results of foo were equal to 3, you would then simply do
        if( $fooval == 3 ) { bar(); }


returned (assuming foo only returned one value per call), you would do
it like this:






        $struct0_2_A_foo = eigenvalues $str_2_A_foo[0];
        # above is $structure[0]->[2]->{'keyA'}->foo;

Quote:

[snip]

> and returns the return values of foo() as one big long list.

Why?  What's wrong with keeping the structure?

Quote:

> Or this, to use a simple slice on a reference:

>     ($arrayref)->[0..15]; # The () gives me list context

No, the () do not give you a list context.  Making a change like that
would break quite a bit of old code.  However, to get what you want, you
could do:

        $arrayref->[all(0..15)];

Quote:
> Without changing the behaviour of this:

>     # Still returns boring old $arrayref->[0]
>     $arrayref->[0..15];

> or this:

>     # Still returns boring old $arrayref->[15]
>     $arrayref->[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];

But it would break things like:

Quote:
> I was looking at perly.y and I was kind of thinking that I would need
> to change the various 'term ARROW ...' rules to do some sort of check
> on the left-hand side.

> Is this worth investigating?  Is there any chance that such behaviour
> would ever be integrated into Perl 5?  What about Perl 6?

There's a proposal by Damian Conway to introduce superpositions into
perl 6, though it might become Data::Superpositions.

Quote:
> Thanks for any feedback!

> - D



--

7835 1ddf07 23a871 72656b63); print map {$e=1;for(split//){$e*=$_};pack
'V',$e} qw(ptk ppppprre pperrrlau ppppphc ppjsa r);


Wed, 12 Nov 2003 17:27:13 GMT  
 
 [ 5 post ] 

 Relevant Pages 

1. PROBLEMS WITH TTABLE and ASCII files

2. Distributive -> and indirect slices

3. Distributive list operators.

4. CGI.pm distributive tag enhancement

5. CGI.pm and distributive property of shortcuts

6. unsuscribe

7. How do I put a grid field into Field Edit mode?

8. >>>>>EXPERIENCED CGI PROGRAMMER NEEDED FOR PROJECT

9. Can <> be indirect <$nullstring>

10. Need help ASAP with this Pascal Program

11. Winsock

12. <<<<<< HELP >>>>>>>>

 

 
Powered by phpBB® Forum Software