Nicholas Clark wrote:
On Tue, Mar 17, 2009 at 06:45:51PM +0100, Jonathan Worthington wrote:
Nicholas Clark wrote:
Yay. As does this?
my @bar = 1,2,3;
sub swatest {
(state @foo) = @bar;
my $x = @foo.perl;
@foo[0]++;
return $x
}
is swatest(), '[1, 2, 3]', 'array state initialized correctly';
is swatest(), '[1, 2, 3]', 'array state retained between calls';
[which IIRC is specified as being different]
You had me thinking, "huh", for a moment before I realized why it's
different. And yes, Rakudo gets the answers you expect. Added to the
tests, thanks again!
I don't understand why it's different, but Larry says that it is.
It's different because (state @foo) on the LHS is creating a list
containing the variable @foo (which you just happen to be declaring too)
and then doing a list assignment (which just goes over the list of
containers on the LHS). Whereas state @foo = @bar is declaring an @foo
that is initialized to @bar (and since it's an initialization, subject
to the initialized-once semantics). It's like how my ($a, $b) differs
from (my $a, $b).
(The current way Perl 5 builds its optree, you can't tell my (@foo) = @bar; and
(my @foo) = @bar; apart, so it isn't currently different in Perl 5, hence why
state (@foo) = @bar; is currently a syntax error. But this does now mean that a
Perl 6 implementation can do state variables better than Perl 5, which can only
do initalisers on a scalar.)
Yeah, but Perl 5 beat us to having some implementation of them at all! :-)
Jonathan