Array#rest

I find myself frequently using array slice of 1..-1, to pass the rest of an
array onto something. While this is a reasonably concise syntax it is not the
most readable. I was curious if there had ever been interest in a rest operator
on an array?

For example

a = [1,2,3,4]
a[1..-1] # -> [2,3,4]
a.rest # -> [2,3,4]

I realize this might cause a few people to write programs in a more list
processing stance, for which the current arrays are probably not best suited.
However, the majority of the times I use this operator is for say reading in a
command as a the first arg, and passing the rest of the elements as the
parameters, and thus it would not be a performance issue. Rest should also have
the same copy symantics as the 1..-1 slice.

Any particular objections to this? Should I make this an RCR?

Charles Comstock

"Charles Comstock" <cc1@cec.wustl.edu> schrieb im Newsbeitrag
news:Pine.LNX.4.44.0406110124410.15301-100000@earwig.int.cec.wustl.edu...

I find myself frequently using array slice of 1..-1, to pass the rest of

an

array onto something. While this is a reasonably concise syntax it is not

the

most readable. I was curious if there had ever been interest in a rest

operator

on an array?

For example

a = [1,2,3,4]
a[1..-1] # -> [2,3,4]
a.rest # -> [2,3,4]

I realize this might cause a few people to write programs in a more list
processing stance, for which the current arrays are probably not best

suited.

However, the majority of the times I use this operator is for say reading

in a

command as a the first arg, and passing the rest of the elements as the
parameters, and thus it would not be a performance issue. Rest should

also have

the same copy symantics as the 1..-1 slice.

Any particular objections to this? Should I make this an RCR?

If you want to do something about this I'd prefer a symmetric solution like
Array#head and Array#tail or Array#car and Array#cdr.

Btw: is "rest" in English the same as in German? I always thought "rest"
rather means "pause" than "reminder"...

Kind regards

    robert

Charles Comstock wrote:

a = [1,2,3,4]
a[1..-1] # -> [2,3,4]
a.rest # -> [2,3,4]
Any particular objections to this? Should I make this an RCR?

I already tried to introduce this into Ruby as a.last(-1), but matz didn't seem to like it. I wish you good luck with a new RCR. :slight_smile:

Charles Comstock <cc1@cec.wustl.edu> wrote in message news:

a = [1,2,3,4]
a[1..-1] # -> [2,3,4]
a.rest # -> [2,3,4]

In what way are you after something different from Array.shift?

a = [1,2,3,4]
wanted = a.shift # 1
passed = a # [2,3,4]

Tom

first / rest is symmetric...
head / tail unix commands don't default to 1 "line"
car + cdr have crappy names.
i'm sure there is something better for this :slight_smile:

Alex

···

On Fri, Jun 11, 2004 at 08:33:38PM +0900, Robert Klemme wrote:

> Any particular objections to this? Should I make this an RCR?

If you want to do something about this I'd prefer a symmetric solution like
Array#head and Array#tail or Array#car and Array#cdr.

Hi --

"Charles Comstock" <cc1@cec.wustl.edu> schrieb im Newsbeitrag
news:Pine.LNX.4.44.0406110124410.15301-100000@earwig.int.cec.wustl.edu...
> I find myself frequently using array slice of 1..-1, to pass the rest of
an
> array onto something. While this is a reasonably concise syntax it is not
the
> most readable. I was curious if there had ever been interest in a rest
operator
> on an array?
>
> For example
>
> a = [1,2,3,4]
> a[1..-1] # -> [2,3,4]
> a.rest # -> [2,3,4]
>
> I realize this might cause a few people to write programs in a more list
> processing stance, for which the current arrays are probably not best
suited.
> However, the majority of the times I use this operator is for say reading
in a
> command as a the first arg, and passing the rest of the elements as the
> parameters, and thus it would not be a performance issue. Rest should
also have
> the same copy symantics as the 1..-1 slice.
>
> Any particular objections to this? Should I make this an RCR?

If you want to do something about this I'd prefer a symmetric solution like
Array#head and Array#tail or Array#car and Array#cdr.

I agree, though my first choice would be just to keep it as is. I'm
not entirely sure why... it could just be jitters about creeping
method multiplication, though I do try not to confuse RCRs in my mind
with RCs :slight_smile:

Btw: is "rest" in English the same as in German? I always thought "rest"
rather means "pause" than "reminder"...

s/reminder/remainder/ :slight_smile: It has several meanings (it can be
equivalent to "Ruhe"), including "remainder": "While he stayed, the
rest of us went home." But when you want to emphasize that everything
except what remains has been destroyed, you would say, e.g., "the
remains of the building". (As opposed to: "They painted the second
floor but not the rest of the building.")

David

···

On Fri, 11 Jun 2004, Robert Klemme wrote:

--
David A. Black
dblack@wobblini.net

Btw: is "rest" in English the same as in German? I always thought "rest"
rather means "pause" than "reminder"...

It has both meanings.

(in swedish we have 'rast' for pause, and 'rest' for remainder)

You can refer to the first and rest of the list, in fact I had those
bound when I first started using scheme, as opposed to car & cdr until
I realized the value of cadr, cadar and the like. We already have
first and last, so I assumed rest would be reasonably symmetric with
this. a.last(a.size-1) doesn't look very good either, though it might
be clearer then [1..-1].

With regards to english use, rest does mean pause, but it is also quite
commonly used to refer to the remainder of something. I'd almost
hazard to guess they are equally used. Certainly rest is used more
often then remainder in common speech I think.

Charles Comstock

···

On Fri, 11 Jun 2004, Robert Klemme wrote:

If you want to do something about this I'd prefer a symmetric solution like
Array#head and Array#tail or Array#car and Array#cdr.

Btw: is "rest" in English the same as in German? I always thought "rest"
rather means "pause" than "reminder"...

I don't want a destructive function. A number of times I have used the shift
and the remainder, but there are a number of times you want a non destructive
copy of the rest of the list. Hence rest ;p

Charles Comstock

···

On 11 Jun 2004, Tom Counsell wrote:

Charles Comstock <cc1@cec.wustl.edu> wrote in message news:
> a = [1,2,3,4]
> a[1..-1] # -> [2,3,4]
> a.rest # -> [2,3,4]

In what way are you after something different from Array.shift?

a = [1,2,3,4]
wanted = a.shift # 1
passed = a # [2,3,4]

Tom

What about

#begin == slice(0..-2)
#end == slice(1..-1)

···

On Friday 11 June 2004 13:41, Alexander Kellett wrote:

On Fri, Jun 11, 2004 at 08:33:38PM +0900, Robert Klemme wrote:
> > Any particular objections to this? Should I make this an RCR?
>
> If you want to do something about this I'd prefer a symmetric solution
> like Array#head and Array#tail or Array#car and Array#cdr.

first / rest is symmetric...
head / tail unix commands don't default to 1 "line"
car + cdr have crappy names.
i'm sure there is something better for this :slight_smile:

--
Simon Strandgaard

"David A. Black" <dblack@wobblini.net> schrieb im Newsbeitrag
news:Pine.LNX.4.44.0406110437280.1536-100000@wobblini...

Hi --

>
> "Charles Comstock" <cc1@cec.wustl.edu> schrieb im Newsbeitrag
>

news:Pine.LNX.4.44.0406110124410.15301-100000@earwig.int.cec.wustl.edu...

> > I find myself frequently using array slice of 1..-1, to pass the rest

of

> an
> > array onto something. While this is a reasonably concise syntax it is

not

> the
> > most readable. I was curious if there had ever been interest in a

rest

> operator
> > on an array?
> >
> > For example
> >
> > a = [1,2,3,4]
> > a[1..-1] # -> [2,3,4]
> > a.rest # -> [2,3,4]
> >
> > I realize this might cause a few people to write programs in a more

list

> > processing stance, for which the current arrays are probably not best
> suited.
> > However, the majority of the times I use this operator is for say

reading

> in a
> > command as a the first arg, and passing the rest of the elements as

the

> > parameters, and thus it would not be a performance issue. Rest should
> also have
> > the same copy symantics as the 1..-1 slice.
> >
> > Any particular objections to this? Should I make this an RCR?
>
> If you want to do something about this I'd prefer a symmetric solution

like

> Array#head and Array#tail or Array#car and Array#cdr.

I agree, though my first choice would be just to keep it as is. I'm
not entirely sure why... it could just be jitters about creeping
method multiplication, though I do try not to confuse RCRs in my mind
with RCs :slight_smile:

> Btw: is "rest" in English the same as in German? I always thought

"rest"

> rather means "pause" than "reminder"...

s/reminder/remainder/ :slight_smile:

Darn! Yes, of course I meant "remainder".

It has several meanings (it can be
equivalent to "Ruhe"), including "remainder": "While he stayed, the
rest of us went home."

Ah, yes. Forgot that one. It sounded odd at first sight but this example
feels perfectly ok.

But when you want to emphasize that everything
except what remains has been destroyed, you would say, e.g., "the
remains of the building". (As opposed to: "They painted the second
floor but not the rest of the building.")

Thanks for the lengthy explanation (or was it "expiration"? :-))))

Regards

    robert

···

On Fri, 11 Jun 2004, Robert Klemme wrote:

"Linus Sellberg" <linse428@student.liu.se> schrieb im Newsbeitrag
news:cac6np$r1b$1@news.island.liu.se...

> Btw: is "rest" in English the same as in German? I always thought

"rest"

> rather means "pause" than "reminder"...

It has both meanings.

(in swedish we have 'rast' for pause, and 'rest' for remainder)

Ha, in German, too! :slight_smile: There's so nice words like "Raststätte",
"Rastplatz" etc. :-))

    robert

Alexander Kellett <ruby-lists@lypanov.net> writes:

first / rest is symmetric...
head / tail unix commands don't default to 1 "line"
car + cdr have crappy names.

Array#car and Array#cdr were the first one that came into my
mind... And the name is only crappy when not used to it...

then we can even define Array#cadr and so on :wink:

Patrick

Hi,

I don't want a destructive function. A number of times I have used the shift
and the remainder, but there are a number of times you want a non destructive
copy of the rest of the list. Hence rest ;p

If you don't want to destroy the original list you can use the splat operator
in an assignment:

a = [ 1, 2, 3, 4 ]
# => [1, 2, 3, 4]
first, *rest = a
# => [1, 2, 3, 4]
first
# => 1
rest
# => [2, 3, 4]

Florian Frank

···

On 11.06.2004, at 18:23, Charles Comstock wrote:

"Alexander Kellett" <ruby-lists@lypanov.net> wrote in message news:20040611112816.GA2067@loki...

first / rest is symmetric...
head / tail unix commands don't default to 1 "line"
car + cdr have crappy names.
i'm sure there is something better for this :slight_smile:

Could be take / drop (with optional argument, number of items):

[1,2,3,4].take --> 1
[1,2,3,4].take(1) --> 1 # or can be [1]
[1,2,3,4].take(2) --> [1,2]
[1,2,3,4].drop --> [2,3,4]
[1,2,3,4].drop(2) --> [3,4]
[1,2,3,4].take(-3) --> [2,3,4]
[1,2,3,4].drop(-1) --> [1,2,3]

And in some language there was a pair 'first / butfirst'.

···

--
Georgy Pruss
E#Mail: 'naabbcaDaddaLryDwksvKmyw'.tr('a-zA-Z','0-9a-z.@')

Hi --

···

On Fri, 11 Jun 2004, Patrick Gundlach wrote:

Alexander Kellett <ruby-lists@lypanov.net> writes:

> first / rest is symmetric...
> head / tail unix commands don't default to 1 "line"
> car + cdr have crappy names.

Array#car and Array#cdr were the first one that came into my
mind... And the name is only crappy when not used to it...

then we can even define Array#cadr and so on :wink:

What problem would this solve?

David

--
David A. Black
dblack@wobblini.net

Yea I know I can do it like that, but sometimes I don't want the extra variable
running around. The most recent case I wanted a rest function was a situation
where I had an array in which the first arg was used to select the command
object and then the rest of the array was used as the parameter list to the
command's instanciation. I wanted to keep the original input as a single
array so that I could print it out for debug output later if I needed to,
keeping the command name so it was clearer. Obviously I could seperate it into
command name and params and keep around the original input, but I really only
need each of the parts once, so it seemed logical to just grab out the parts I
needed when I passed them as parameters. It's not an issue of not knowing how
to split them, or even that the method isn't already available through
slice(1..-1), I just thought that array rest would be more readable in this
case. It's not something really frequent but I find myself using stuff like
this here and there, and it just seemed like a useful function to have. It
just seemed to make sense what with ruby already having a first function.

On a side note, I had to double check your above example. I knew you could
split like that, but I didn't realize that it performed a copy and was not
referencing the original parts of a. I suppose it is more useful that way, and
am glad it is, but my gut reaction to the symantics of that was that it
performed like ='s generally does, acting as an alias instead. You learn
something every day I guess.

Charles Comstock

···

On Sat, 12 Jun 2004, Florian Frank wrote:

Hi,

On 11.06.2004, at 18:23, Charles Comstock wrote:
> I don't want a destructive function. A number of times I have used
> the shift
> and the remainder, but there are a number of times you want a non
> destructive
> copy of the rest of the list. Hence rest ;p

If you don't want to destroy the original list you can use the splat
operator
in an assignment:

a = [ 1, 2, 3, 4 ]
# => [1, 2, 3, 4]
first, *rest = a
# => [1, 2, 3, 4]
first
# => 1
rest
# => [2, 3, 4]

Nice! And probably efficient too.
That is an often overlooked feature of ruby.
It somehow reminds me of Prolog:
  ([First|Tail], A).
Free/Bound variables is a missing concept in
Ruby today (not talking about backtracking).
I am working on that (the former, matching).

Yours,

JeanHuguesRobert

···

At 04:05 12/06/2004 +0900, you wrote:

Hi,

On 11.06.2004, at 18:23, Charles Comstock wrote:

I don't want a destructive function. A number of times I have used the shift
and the remainder, but there are a number of times you want a non destructive
copy of the rest of the list. Hence rest ;p

If you don't want to destroy the original list you can use the splat operator
in an assignment:

a = [ 1, 2, 3, 4 ]
# => [1, 2, 3, 4]
first, *rest = a
# => [1, 2, 3, 4]
first
# => 1
rest
# => [2, 3, 4]

Florian Frank

-------------------------------------------------------------------------
Web: @jhr is virteal, virtually real
Phone: +33 (0) 4 92 27 74 17

"Alexander Kellett" <ruby-lists@lypanov.net> wrote in message news:20040611112816.GA2067@loki...

first / rest is symmetric...
head / tail unix commands don't default to 1 "line"
car + cdr have crappy names.
i'm sure there is something better for this :slight_smile:

Could be take / drop (with optional argument, number of items):

[1,2,3,4].take --> 1
[1,2,3,4].take(1) --> 1 # or can be [1]
[1,2,3,4].take(2) --> [1,2]
[1,2,3,4].drop --> [2,3,4]
[1,2,3,4].drop(2) --> [3,4]
[1,2,3,4].take(-3) --> [2,3,4]
[1,2,3,4].drop(-1) --> [1,2,3]

And in some language there was a pair 'first / butfirst'.
Georgy Pruss

That is what I ended up in some language I designed. I
was not perfectly happy with the result, but that was
the best I found. Was more like but_first() however
(well... it actually was butFirst(), Smalltalk camelCase).
It worked on strings, lists and arrays and was the main
style for iterating:
  while item = a_list.first()
    a_list = a_list.but_first()
    xxx
  end
I for sure prefer Ruby's
  for item in a_list do
    xxx
  end
or even more Rubyish (or Smalltalkish) I guess:
  a_list.each do |item|
    xxx
  end
It was efficient because I had implemented copy-on-write
optimization and but_first() was just a pointer increment.

Yours,

JeanHuguesRobert

···

At 12:03 12/06/2004 +0900, you wrote:

E#Mail: 'naabbcaDaddaLryDwksvKmyw'.tr('a-zA-Z','0-9a-z.@')

-------------------------------------------------------------------------
Web: @jhr is virteal, virtually real
Phone: +33 (0) 4 92 27 74 17

Greenspun's 10th :slight_smile:

martin

···

David A. Black <dblack@wobblini.net> wrote:

On Fri, 11 Jun 2004, Patrick Gundlach wrote:
>
> then we can even define Array#cadr and so on :wink:

What problem would this solve?