Why are "Array#push" and "pop" not "push!" and "pop!"?

Few more methods where the bang only indicates in-place operation:

String#succ!, Array#reverse!, Array#collect!, Array#sort!

Regards,
Jordan

···

On Dec 4, 5:23 am, MonkeeSage <MonkeeS...@gmail.com> wrote:

On Dec 4, 3:02 am, "David A. Black" <dbl...@rubypal.com> wrote:

> They inherently change their receivers, but that's a separate matter
> from the !.

Well...99% of the time it is, except when the ! only serves to
indicate that it operates in-place (String#reverse!, Hash#update!, and
probably a few others I can't think of offhand*). That's why I
characterized the ! as "either-or-both" regarding in-place/dangerous.
Even if it's not a good idea or breaks with the common usage, it is
used that way at least a few times in stdlib.

* Oh yeah, and I just remembered #power! (on Bignum I think) which
isn't dangerous and doesn't modify the receiver...it just raises to a
power. Where the heck did the bang come from?!

Regards,
Jordan

Hi --

They inherently change their receivers, but that's a separate matter
from the !.

Well...99% of the time it is, except when the ! only serves to
indicate that it operates in-place (String#reverse!, Hash#update!, and
probably a few others I can't think of offhand*). That's why I
characterized the ! as "either-or-both" regarding in-place/dangerous.

I'm not sure I follow, so this may not be relevant, but in-place
changes (changes to the receiver) are one form of "danger", in this
sense. They're just not the only form.

Even if it's not a good idea or breaks with the common usage, it is
used that way at least a few times in stdlib.

I don't know of any that don't come in pairs, where the ! one
indicates "danger" (reverse/reverse!, exit/exit!, etc.).

* Oh yeah, and I just remembered #power! (on Bignum I think) which
isn't dangerous and doesn't modify the receiver...it just raises to a
power. Where the heck did the bang come from?!

Good question. I see this in ri but I don't see it actually on any
objects. I'm not sure what it is.

David

···

On Tue, 4 Dec 2007, MonkeeSage wrote:

On Dec 4, 3:02 am, "David A. Black" <dbl...@rubypal.com> wrote:

--
Upcoming training by David A. Black/Ruby Power and Light, LLC:
    * Intro to Rails, London, UK, December 3-6 (by Skills Matter)
See http://www.rubypal.com for details and 2008 announcements!

Well, slice(-1) and slice!(-1) are equivalents for pop (non-modifying)
and pop! (modifying), right?

···

On Dec 4, 2007 1:04 PM, Bill Kelly <billk@cts.com> wrote:

From: "David A. Black" <dblack@rubypal.com>
>
> [...] I just
> think that Matz's abstraction of these as "dangerous", and dedication
> of the ! to expressing that abstraction, is strikingly elegant and has
> the weight of some kind of logic behind it. It hits a narrower target
> -- it means that there's a whole class of tricky (or whatever) methods
> that have to find some other way to express their trickiness -- but I
> think it's worth it.

Ah. I think I understand your viewpoint better now; thanks.

(And if nothing else, at least we can both agree on the "hits a
narrower target" part. <grin> )

Regards,

Bill

Hi --

···

On Tue, 4 Dec 2007, MonkeeSage wrote:

On Dec 4, 5:23 am, MonkeeSage <MonkeeS...@gmail.com> wrote:

On Dec 4, 3:02 am, "David A. Black" <dbl...@rubypal.com> wrote:

They inherently change their receivers, but that's a separate matter
from the !.

Well...99% of the time it is, except when the ! only serves to
indicate that it operates in-place (String#reverse!, Hash#update!, and
probably a few others I can't think of offhand*). That's why I
characterized the ! as "either-or-both" regarding in-place/dangerous.
Even if it's not a good idea or breaks with the common usage, it is
used that way at least a few times in stdlib.

* Oh yeah, and I just remembered #power! (on Bignum I think) which
isn't dangerous and doesn't modify the receiver...it just raises to a
power. Where the heck did the bang come from?!

Regards,
Jordan

Few more methods where the bang only indicates in-place operation:

String#succ!, Array#reverse!, Array#collect!, Array#sort!

In-place modification is, I think, definitely the most common form of
!-style "danger". It's not the only form, though.

David

--
Upcoming training by David A. Black/Ruby Power and Light, LLC:
    * Intro to Rails, London, UK, December 3-6 (by Skills Matter)
See http://www.rubypal.com for details and 2008 announcements!

Hi --

>> They inherently change their receivers, but that's a separate matter
>> from the !.

> Well...99% of the time it is, except when the ! only serves to
> indicate that it operates in-place (String#reverse!, Hash#update!, and
> probably a few others I can't think of offhand*). That's why I
> characterized the ! as "either-or-both" regarding in-place/dangerous.

I'm not sure I follow, so this may not be relevant, but in-place
changes (changes to the receiver) are one form of "danger", in this
sense. They're just not the only form.

Don't mind me, I'm just over-analyzing. :stuck_out_tongue_winking_eye: After remaking that
"danger" can be ambiguous above, I posted a characterization of !
where I tried to disambiguate "danger" in the following way: "Causes
some side-effect that is incompatible or sufficiently different from
the non-bang version". Since everything is "dangerous" in ruby from
the perspective of a haskeller, I thought it might be helpful to
differentiate between mutation of the receiver (not generally
considered dangerous in ruby), and incompatible/unexpected behavior as
compared to the non-bang version. Most bang-methods, I think, do both.

> Even if it's not a good idea or breaks with the common usage, it is
> used that way at least a few times in stdlib.

I don't know of any that don't come in pairs, where the ! one
indicates "danger" (reverse/reverse!, exit/exit!, etc.).

I agree. That was one of my reasons for not supporting "push!" --
along with the fact that the method name is fully descriptive, and
that a ! suffix would be confusing, it would be unbalanced (q.v.,
previous post).

> * Oh yeah, and I just remembered #power! (on Bignum I think) which
> isn't dangerous and doesn't modify the receiver...it just raises to a
> power. Where the heck did the bang come from?!

Good question. I see this in ri but I don't see it actually on any
objects. I'm not sure what it is.

It appears to be an alias of an alias (power! -> ** -> rpower).
Bignum#rpower returns a new Rational, so, indeed, the operation is non-
dangerous and does not mutate the receiver...I guess matz just had an
extra "!" lying around and didn't want to waste it, heh. :wink:

David

--
Upcoming training by David A. Black/Ruby Power and Light, LLC:
    * Intro to Rails, London, UK, December 3-6 (by Skills Matter)
Seehttp://www.rubypal.comfor details and 2008 announcements!

Regards,
Jordan

···

On Dec 4, 7:00 am, "David A. Black" <dbl...@rubypal.com> wrote:

On Tue, 4 Dec 2007, MonkeeSage wrote:
> On Dec 4, 3:02 am, "David A. Black" <dbl...@rubypal.com> wrote:

Well...that's kind of cheating. Heh. :wink: Semantically, they are very
different; though pragmatically you get the same result. Kind of like
a car hitting you at 50 k/mph gets the same result as you hitting a
car at 50 k/mph, even though the car traveling 50 k/mph and yourself
traveling 50 k/mph are very different. For perhaps a better
analogy...these two do the same thing, even though they have very
different semantics and implementations:

p [1,2,3,4].last #=> 4

arr = [1,2,3,4]
count = 0
arr.each { | e |
  if count == arr.size-1
    p e
  end
  count += 1
}
# => 4

The first is obviously the correct choice, even though you *can* do
the second if you really wanted to.

Regards,
Jordan

···

On Dec 4, 1:31 pm, Christian von Kleist <cvonkle...@gmail.com> wrote:

On Dec 4, 2007 1:04 PM, Bill Kelly <bi...@cts.com> wrote:

> From: "David A. Black" <dbl...@rubypal.com>

> > [...] I just
> > think that Matz's abstraction of these as "dangerous", and dedication
> > of the ! to expressing that abstraction, is strikingly elegant and has
> > the weight of some kind of logic behind it. It hits a narrower target
> > -- it means that there's a whole class of tricky (or whatever) methods
> > that have to find some other way to express their trickiness -- but I
> > think it's worth it.

> Ah. I think I understand your viewpoint better now; thanks.

> (And if nothing else, at least we can both agree on the "hits a
> narrower target" part. <grin> )

> Regards,

> Bill

Well, slice(-1) and slice!(-1) are equivalents for pop (non-modifying)
and pop! (modifying), right?

just means that the whole thing
becomes method-name soup and has *no* meaning.

That is not true. I agree that it should not be used
in other ways than how pretty everyone else uses it.

However, it does not have *no* meaning anymore, it
simply has a *different* meaning now. If you want to
use it (i.e define this different meaning) and how
you want to use it, is up to you - for example,
you could do something like:

  def nuke!
    FileUtils.rm_rf /playing_games_during_worktime # boss coming in!
  end

And you would still be aware that the method does
something dangerous.

I used to do this years ago, until I later found out
I hated to be surprised by methods with ! which
behave differently :wink:

···

--
Posted via http://www.ruby-forum.com/\.

Good point. :slight_smile:

I remember having the same question about shift/unshift when I first
learned Ruby. I remember doing something like the following:

item = items.shift!

...and I was surprised to see a NoMethodError. It seemed to violate
the rule I supposed existed: all destructive methods end in !

It is an interesting debate, but I suppose it's a bit of a moot point
now; it's too late to change these basic methods, even if we wanted
to.

···

On Dec 4, 2007 3:00 PM, MonkeeSage <MonkeeSage@gmail.com> wrote:

On Dec 4, 1:31 pm, Christian von Kleist <cvonkle...@gmail.com> wrote:
> On Dec 4, 2007 1:04 PM, Bill Kelly <bi...@cts.com> wrote:
>
>
>
>
>
> > From: "David A. Black" <dbl...@rubypal.com>
>
> > > [...] I just
> > > think that Matz's abstraction of these as "dangerous", and dedication
> > > of the ! to expressing that abstraction, is strikingly elegant and has
> > > the weight of some kind of logic behind it. It hits a narrower target
> > > -- it means that there's a whole class of tricky (or whatever) methods
> > > that have to find some other way to express their trickiness -- but I
> > > think it's worth it.
>
> > Ah. I think I understand your viewpoint better now; thanks.
>
> > (And if nothing else, at least we can both agree on the "hits a
> > narrower target" part. <grin> )
>
> > Regards,
>
> > Bill
>
> Well, slice(-1) and slice!(-1) are equivalents for pop (non-modifying)
> and pop! (modifying), right?

Well...that's kind of cheating. Heh. :wink: Semantically, they are very
different; though pragmatically you get the same result. Kind of like
a car hitting you at 50 k/mph gets the same result as you hitting a
car at 50 k/mph, even though the car traveling 50 k/mph and yourself
traveling 50 k/mph are very different. For perhaps a better
analogy...these two do the same thing, even though they have very
different semantics and implementations:

p [1,2,3,4].last #=> 4

arr = [1,2,3,4]
count = 0
arr.each { | e |
  if count == arr.size-1
    p e
  end
  count += 1
}
# => 4

The first is obviously the correct choice, even though you *can* do
the second if you really wanted to.

Regards,
Jordan

Hi --

just means that the whole thing
becomes method-name soup and has *no* meaning.

That is not true. I agree that it should not be used
in other ways than how pretty everyone else uses it.

However, it does not have *no* meaning anymore, it
simply has a *different* meaning now.

Not that I've heard. I'll defer to Matz on that one.

If you want to use it (i.e define this different meaning) and how
you want to use it, is up to you - for example, you could do
something like:

def nuke!
   FileUtils.rm_rf /playing_games_during_worktime # boss coming in!
end

And you would still be aware that the method does
something dangerous.

Yes, as I said before, we can all do whatever we want with !, and end
up with no convention and no pattern and therefore no meaning. If we
all invent new meanings for it, then it has none, in the sense that
when I see it, I won't know what it means.

The parser will certainly let you do it. I just have not seen any
evidence that anyone has any ideas on this that are remotely as good
as Matz's. So I've never understood what the temptation is to
improvise new meanings for it.

I used to do this years ago, until I later found out
I hated to be surprised by methods with ! which
behave differently :wink:

But that's the point -- the ! *tells* you that they behave
differently from their "non-dangerous" counterparts. That's the
ingenuity of it.

David

···

On Tue, 4 Dec 2007, Marc Heiler wrote:

--
Upcoming training by David A. Black/Ruby Power and Light, LLC:
    * Intro to Rails, London, UK, December 3-6 (by Skills Matter)
See http://www.rubypal.com for details and 2008 announcements!

Hi --

Good point. :slight_smile:

I remember having the same question about shift/unshift when I first
learned Ruby. I remember doing something like the following:

item = items.shift!

...and I was surprised to see a NoMethodError. It seemed to violate
the rule I supposed existed: all destructive methods end in !

We're lucky that there's no such rule. Imagine:

   "string" <<! "more text"
   array.clear!
   obj.instance_variable_set!
   (etc.)

:slight_smile:

The use of destructive-sounding names (or, where appropriate,
non-destructive-sounding ones plus the "danger" flag) works out well.
The only somewhat anomalous case I know of is delete(!), where
String#delete is not destructive but Array#delete is. I'm not sure why
those differ from each other in that respect.

David

···

On Wed, 5 Dec 2007, Christian von Kleist wrote:

--
Upcoming training by David A. Black/Ruby Power and Light, LLC:
    * Intro to Rails, London, UK, December 3-6 (by Skills Matter)
See http://www.rubypal.com for details and 2008 announcements!