OK, I think I've got an implementation. Here's what I'm thinking:
First, splice and slice functions:
sub list_splice_vmeth {
my ($list, $offset, $length, @replace) = @_;
return list_slice_vmeth($list, $offset, $length)
unless (@replace);
# Destructive!
splice @$list, $offset, $length, @replace;
return "";
}
sub list_slice_vmeth {
my ($list, $offset, $length) = @_;
my @newlist = @$list;
return [ splice(@newlist, $offset, $length) ]
if (defined $length);
return [ splice(@newlist, $offset) ]
if (defined $offset);
return [ splice(@newlist) ];
}
And the LIST_OPS:
'splice' => \&list_splice_vmeth,
'slice' => \&list_slice_vmeth,
'first' => sub {
my $list = shift;
return $list->[0] unless @_ && int $_[0] > 0;
return list_slice_vmeth($list, 0, $_[0]);
},
'last' => sub {
my $list = shift;
return $list->[$#$list] unless @_;
return list_slice_vmeth($list, -$_[0], $_[0]);
},
slice is not destructive, and ignores attempts to modify.
splice is destructive, and returns nothing, when called with three or
more arguments; otherwise, it's identical to slice.
last and first are as they were.
Outstanding issues/suggestions:
* Passing mutliple things into @replace (in splice) does not die, like
Mark suggested, but...
* slice cannot be used to modify the list that comes back, so perhaps
slice should accept @replace and modify the return list (not the
original list)? Like the splice I had earlier:
sub list_slice_vmeth {
my ($list, $offset, $length, @replace) = @_;
my @newlist = @$list;
if (@replace) {
splice @newlist, $offset, $length, @replace;
return \@newlist;
}
return [ splice(@newlist, $offset, $length) ]
if (defined $length);
return [ splice(@newlist, $offset) ]
if (defined $offset);
return [ splice(@newlist) ];
}
This is non-destructive, and seems to maintain the balance between
people expecting this to be named 'slice' and doing the above, and
people expecting something called 'splice' to be destructive when called
with 3 or more arguments.
Opinions? If we can agree on this, I'll commit this into Stash.pm, and
update tests and docs. Mark, did you say you have some tests for first,
last, slice, and splice?
(darren)
--
A sect or party in an elegant incognito devised to save a man from
the vexation of thinking.
-- Ralph Waldo Emerson