Today I saw a blog by Guido van Rossum, creator of Python, on
www.artima.com in which he criticized Ruby's mutable strings - saying
that of such a horror he could ne'er conceive, or something :)
Anyway, all the discussion I've seen about (im)mutable strings has
focused on implementation and efficiency. LISP may be a
counter-example, but I'm not sure, and its paradigm is different. I'd
like to know what the design considerations are.
So, is van Rossum's point valid? I must say, immutable strings sound
elegant to me for some reason I can't work out, but then Ruby has
oh-so-cool symbols anyway. What are the pros and cons of Ruby and
Python on the string department?
BTW the URL for that blog is http://www.artima.com/weblogs/viewpost.jsp?thread=7589
Gavin
In message "Question: immutable strings as design goal?"
on 03/08/18, Gavin Sinclair <gsin...@soyabean.com.au> writes:
|Today I saw a blog by Guido van Rossum, creator of Python, on
|www.artima.com in which he criticized Ruby's mutable strings - saying
|that of such a horror he could ne'er conceive, or something :)
If mutable strings are horror, mutable dictionaries should be as well.
The one with such standard should go to side-effect free language like
Haskell. ;-)
I rarely have such problems caused by mutable strings. Besides, Ruby
is not a language to keep people away from horror. You can write
ugly, scary, or dangerous programs in Ruby, if you want. It's cost
for freedom.
matz.
> I rarely have such problems caused by mutable strings. Besides, Ruby
> is not a language to keep people away from horror. You can write
> ugly, scary, or dangerous programs in Ruby, if you want. It's cost
> for freedom.
>
This points to an important "philosophical" difference that stands
out to me when comparing Ruby and Python: Python gives me the feeling of
trying to be a "Language for the Masses" (LFM) and tries to put
restrictions on what can be done. You need to format your code in a certain
way, your strings (but only a minority of other objects) are immutable by
default etc. As discussed on ll1-discuss mailing list and
other places LFM's are in contrast to LFSP's (Language for Smart People /
experts) that tries to give you as much power as possible.
To me the LFM thinking is absurd and even inhumane since it (ironically
enough) says that there is an elite that know the area well enough to
decide what other people is allowed to use.
To me matz goal seems to be for less of an LFM than Guidos.
Then again I have too little experience with Python vs. Ruby to actually
know. I also may be exaggerating since also matz has his limits (no
macros in Ruby, no multi-methods etc) ;).
Regards,
Robert Feldt
Ps. "Rough" Immutable strings in ruby:
s1 = "a"
s1[0] = ?b
p s1 # => b
def ims(string)
string.freeze
end
s2 = ims "a"
p s1 # => a
s2[0] = ?b # => `[]=': can't modify frozen string (TypeError)
;)
> Hi,
> In message "Question: immutable strings as design goal?"
> on 03/08/18, Gavin Sinclair <gsin...@soyabean.com.au> writes:
> |Today I saw a blog by Guido van Rossum, creator of Python, on
> |www.artima.com in which he criticized Ruby's mutable strings - saying
> |that of such a horror he could ne'er conceive, or something :)
> If mutable strings are horror, mutable dictionaries should be as well.
> The one with such standard should go to side-effect free language like
> Haskell. ;-)
Yes, that thought struck me as well.
> I rarely have such problems caused by mutable strings. Besides, Ruby
> is not a language to keep people away from horror. You can write
> ugly, scary, or dangerous programs in Ruby, if you want. It's cost
> for freedom.
I don't think his thoughts were on freedon vs restrictions. It seemed
that he just thinks strings, for whatever reason, *should* be
immutable, like numbers.
As a counter-point, all the freedom in the Ruby world doesn't allow
you to modify symbols. Guido obviously believes that all strings
should be like that. (And dictionaries, obviously, shouldn't.)
Gavin
________________________________________________________________________
Want to chat instantly with your online friends? Get the FREE Yahoo!
Messenger http://uk.messenger.yahoo.com/
In message "Re: Question: immutable strings as design goal?"
on 03/08/18, Gavin Sinclair <gsin...@soyabean.com.au> writes:
|> I rarely have such problems caused by mutable strings. Besides, Ruby
|> is not a language to keep people away from horror. You can write
|> ugly, scary, or dangerous programs in Ruby, if you want. It's cost
|> for freedom.
|
|I don't think his thoughts were on freedon vs restrictions. It seemed
|that he just thinks strings, for whatever reason, *should* be
|immutable, like numbers.
I know, I know. Don't take my words seriously.
|As a counter-point, all the freedom in the Ruby world doesn't allow
|you to modify symbols. Guido obviously believes that all strings
|should be like that. (And dictionaries, obviously, shouldn't.)
Although you can't change the value of symbols (and numbers),
you can change their instance variables.
matz.
> Am I correct in thinking that as long as you avoid the
> methods ending with an exclamation mark, then your
> strings will be effectively immutable?
>
Not really, see []= in my example code.
Regards,
Robert
In message "Re: Question: immutable strings as design goal?"
on 03/08/18, Robert Feldt <fe...@ce.chalmers.se> writes:
|This points to an important "philosophical" difference that stands
|out to me when comparing Ruby and Python: Python gives me the feeling of
|trying to be a "Language for the Masses" (LFM) and tries to put
|restrictions on what can be done. You need to format your code in a certain
|way, your strings (but only a minority of other objects) are immutable by
|default etc. As discussed on ll1-discuss mailing list and
|other places LFM's are in contrast to LFSP's (Language for Smart People /
|experts) that tries to give you as much power as possible.
|To me matz goal seems to be for less of an LFM than Guidos.
Yes. It's a language for smart wannabe (i.e people trying to be
smart). I myself is one of them.
matz.
String#concat is another popular trap for young players.
Gavin
A string in Ruby seems to me to be just a convenient way of manipulating
a char array, with a bunch of useful methods such as regular expressions
thrown in. It should be treated no more "specially" than any other class
backed by an array. As Ged says, Ruby has the whole immutable value
object model sewn up much more consistently anyway, with the .freeze
method. You can make anything immutable whenever you like - including in
the initialize method of a well-behaved value object.
Looks to me like another victory for matz's commitment to
non-astonishing behaviour - I don't have to learn which objects are
constructed as immutable by default! I'm liking this language more and
more every day.
Now where's that "final" keyword..?
Cheers,
Dan
> String#concat is another popular trap for young players.
That's a weird one. I would probably expect there to be String#concat
and String#concat! with
appropriate implementations.
However, don't forget the #concat operator:
s = "hi"
s << " there"
p s # => "hi there"
For some reason it doesn't surprise me that this modifies s while
#concat does.
- Dan
Thanks,
for nailing down why I find programming in Ruby sooo pleasurable;-))
/Christoph
> On Monday, August 18, 2003, 11:03:50 PM, Yukihiro wrote:
<snip>
> > I rarely have such problems caused by mutable strings. Besides, Ruby
> > is not a language to keep people away from horror. You can write
> > ugly, scary, or dangerous programs in Ruby, if you want. It's cost
> > for freedom.
>
> I don't think his thoughts were on freedon vs restrictions. It seemed
> that he just thinks strings, for whatever reason, *should* be
> immutable, like numbers.
<snip>
There are always performance issues to consider as well. Constantly
creating new strings, especially when working with large ones, is a
major performance hit.
Numbers, symbols, booleans, etc don't have this problem.
--
Ryan Pavlik <rp...@users.sf.net>
"Why are we even *mentioning* semi-regular polyhedrons
and real space?" - 8BT
This is not the reason Python's strings are immutable,
and I don't generally even agree that there's such difference
between Python and Ruby (LFM vs LFSP). You're probably just trying
to flatter yourself. Python is also a rather unsafe language
that lets you do several dangerous but powerful things. Such
as redefining functions, classes or objects, or accessing any member
in a class. Also, What language doesn't force you to format your code
in a certain way? A language with no syntax perhaps? Ruby forces
you to use do/end or {} (or something), Python uses indentation --
not a real difference, don't you think?
Strings, numbers and tuples are immutable in Python so that they
can be used as dictionary keys. I admit that one could do away
with this restriction by just choosing not to alter strings that
are used as dictionary keys. But allowing this to be done could
lead to subtle bugs, and making strings immutable doesn't do much
harm, so why not make them immutable? It's actually just a design
choice that weighted, which would lead to shorter dev times in
general: immutable or mutable strings. Guido thought it was the former.
> So, is van Rossum's point valid?
No it's not. Guido is just insanely jealous that Matz' personal hero is
Larry Wall and not him, and this "omg, immutable strings are horrid"
crap-o-la is the only thing he could come up with.
What a lamer... :>
--
Luc Heinrich - luc...@mac.com
As Robert Feldt pointed out, you can also implement a 'freeze' method,
and if you really don't trust yourself and others, you can implement
the Seattle Ruby Brigade's 'deepfreeze' method (part of their Ruby
audit, which can be found here:
http://sourceforge.net/project/showfiles.php?group_id=50485 ).
Also, while I'm speaking out of ignorance and mere supposition,
wouldn't immutable strings cause difficulties in languages with more
than one writing system? In particular, Korean uses hangul (a phonetic
alphabet) and hanja (Chinese characters) and Japanese uses kanji
(Chinese characters), hiragana (syllabic symbols), katakana (symbols
for foreign words) and furigana (keys to pronounce kanji). Hopefully,
some with knowledge in this area, will correct or confirm my
supposition.
Regards,
Mark
> Robert Feldt <fe...@ce.chalmers.se> wrote in message
> news:<oprt3snc...@mail1.telia.com>...
>> This points to an important "philosophical" difference that stands
>> out to me when comparing Ruby and Python: Python gives me the feeling of
>> trying to be a "Language for the Masses" (LFM) and tries to put
>> restrictions on what can be done. You need to format your code in a
>> certain way, your strings (but only a minority of other objects) are
>> immutable by default etc. As discussed on ll1-discuss mailing list and
>> other places LFM's are in contrast to LFSP's (Language for Smart People
>> /
>> experts) that tries to give you as much power as possible.
>
> This is not the reason Python's strings are immutable,
> and I don't generally even agree that there's such difference
> between Python and Ruby (LFM vs LFSP). You're probably just trying
> to flatter yourself.
>
;)
In so far as I use Ruby you mean? I didn't want to give the impression
that I'm smarter because I use Ruby, but I've seriously tried to
switch over to Python and find it harder cause it makes me feel
more restricted.
But let's not get into a flame war comparing languages (although I must
say Guido has a responsability as a representant for Python so why
should he go around "dissing" Ruby, at least thats the way his blog
comes out to me).
> Python is also a rather unsafe language
> that lets you do several dangerous but powerful things. Such
> as redefining functions, classes or objects, or accessing any member
> in a class. Also, What language doesn't force you to format your code
> in a certain way? A language with no syntax perhaps? Ruby forces
> you to use do/end or {} (or something), Python uses indentation --
> not a real difference, don't you think?
>
Agreed, and I probably was exaggerating a bit. There are other things
than the indentation requirement and immutable strings that I was
thinking of. But overall I'd say they are very similar so the LFM/LSP
debate was not a good metaphor.
> Strings, numbers and tuples are immutable in Python so that they
> can be used as dictionary keys. I admit that one could do away
> with this restriction by just choosing not to alter strings that
> are used as dictionary keys. But allowing this to be done could
> lead to subtle bugs, and making strings immutable doesn't do much
> harm, so why not make them immutable? It's actually just a design
> choice that weighted, which would lead to shorter dev times in
> general: immutable or mutable strings. Guido thought it was the former.
>
Ok, fair enough.
Regards,
Robert
> I'm no matz or Guido (no surprise there), but I would point out that
> Apple's Cocoa has an immutable string class and a mutable string class.
Many of the Cocoa core foundation classes have mutable and immutable
versions of themselves, mainly for thread-safety and speed reasons. The
nice thing about immutable objects is that you can treat them as
atomically accessible primitives, skipping potentially costly (though
necessary) synchronization stuff.
It also allows for the sharing of identical constants--if the compiler can
detect that two different immutable objects are otherwise identical they
can be merged into a single object, though this is rarely done for
anything besides strings.
> Also, while I'm speaking out of ignorance and mere supposition,
> wouldn't immutable strings cause difficulties in languages with more
> than one writing system?
No. String constants are string constants, no matter how they're encoded
or how many characters are in them. The one place that immutable strings
can be problematic is if you're using Unicode and your string constants
use a different normalization form than some of the operations in the
language or library do, but that's more a speed issue than anything else,
since the runtime will end up having to decompose or recompose (depending
on what uses which forms) as the program executes.
Dan
--
::: name: Nikolai Weibull :: aliases: pcp / lone-star / aka :::
::: born: Chicago, IL USA :: loc atm: Gothenburg, Sweden :::
::: page: www.pcppopper.org :: fun atm: gf,lps,ruby,php,war3 :::
main(){printf(&linux["\021%six\012\0"],(linux)["have"]+"fun"-97);}
-----Original Message-----
From: Luc Heinrich [mailto:luc...@mac.com]
Sent: Monday, August 18, 2003 12:42 PM
To: ruby-talk ML
Subject: Re: Question: immutable strings as design goal?
Gavin Sinclair <gsin...@soyabean.com.au> wrote:
> So, is van Rossum's point valid?
No it's not. Guido is just insanely jealous that Matz' personal hero is
Larry Wall and not him, and this "omg, immutable strings are horrid"
crap-o-la is the only thing he could come up with.
What a lamer... :>
> [snip]
> Strings, numbers and tuples are immutable in Python so that they
> can be used as dictionary keys. I admit that one could do away
> with this restriction by just choosing not to alter strings that
> are used as dictionary keys. But allowing this to be done could
> lead to subtle bugs, and making strings immutable doesn't do much
> harm, so why not make them immutable? It's actually just a design
> choice that weighted, which would lead to shorter dev times in
> general: immutable or mutable strings. Guido thought it was the former.
I'll refer to Objective C/Cocoa in this context again. In addition to
providing immutable and mutable string classes, Objective C/Cocoa
provides two dictionary classes, an immutable dictionary class and a
mutable dictionary class.
The idea that strings should have only one value with respect to
mutability strikes me as odd. Odder still is the rationale that this is
for the purpose of having objects to use as dictionary keys. Can't key
mutability be handled at the dictionary level rather than at the level
of the constituents of the dictionary?
And while I'm on the subject, any object can be a key (or value) in a
Ruby hash (one isn't limited to to tuples, strings and numbers for
keys).
And furthermore, if you want to programmatically avoid accidentally
overwriting keys, there are many other ways to do it without even
addressing mutability questions or checking for key existence before
insertion -- for example, draw keys from a Set object, which guarantees
that each key taken from the set will be unique.
Finally, one can easily create, in Ruby alone, an environment with the
same model as mandated in Python, or an environment with the same model
used in Objective C/Cocoa, or any other environment.
There's a reason I prefer Ruby to all other programming languages for
most tasks. It's good to see the difference from other, otherwise quite
appealing languages, like Python.
Regards,
Mark
Ruby gets around this by dup-ing strings used as Hash keys, so the
problem doesn't crop up.
Cheers
Dave
Mutable strings also result in a more complicated implementation. One of
Python's principles is to keep the implementation as simple as possible;
think of it as XP's rule of "Do the simplest thing that can possibly work."
Consider this code:
d = {}
s = 'abc'
d[s] = 1
s.sub!('ab', 'cd') # abc -> cdc
Now what? If dictionaries don't make copies of their keys, then mutating
the key means that the dictionary now stores a key value of "cdc". But
because this probably changed the hash code, it's now in the wrong hash
bucket. When you do d['cdc'], it will look in the wrong hash bucket, find
it empty, and report the key isn't found.
So what's a language implementor to do? You could have some sort of flag on
strings indicating 'this is in a dictionary: no mutation'. You could keep a
list of "all dictionaries this string is used as a key in", and when you
mutate the string rehash all of them. You could make copies of all keys in
dictionaries, but then someone will use a 3Mb string or a tree as a key and
complain that storing keys is slow. You can then try to figure out when
copying keys is necessary and skip it if it isn't. All of this is more code
to write and more code to be a source of subtle bugs.
Immutable strings cut through all this; you don't need code to handle these
cases because they never come up.
Python's design was influenced by Guido's experience with ABC. ABC went for
theoretical completeness and paid for it in implementation complexity.
Numbers were rationals, and users complained how they got mysteriously slow
after a lengthy computation. Dictionaries were AVL trees, with O(lg N) best
performance but a fairly high constant. Python therefore reacted in the
opposite direction, choosing the simplest implementation and avoiding
complexity as much as possible.
--amk (www.amk.ca)
A is for Adam and E is for Eve. B is for bile, blood and bones.
-- Louis Andriessen & Jeroen van der Linden, "The Alphabet Song"
dup-ing and freezing. It would still be possible to modify the Hash key
if the key were not frozen.
Paul
I think the point is that you would have to expressly access the Hash
key to modify it -- modifications to the original string, if it's kept
in existence, won't affect the Hash key.
Regards,
Mark
Indeed, although there's nothing intrinsically wrong with modifying a
hash key (after all, you could have arrays as hash keys, and they're
not frozen). Hash#rehash (and some common sense when it comes to
retaining references to keys) is your friend here.
Also it might be worth mentioning that (I believe) that the keys are
duped using copy-on-write semantics, so there's less overhead that some
might suppose.
Cheers
Dave
> [snip]
> Mutable strings also result in a more complicated implementation. One
> of
> Python's principles is to keep the implementation as simple as
> possible;
> think of it as XP's rule of "Do the simplest thing that can possibly
> work."
I think this is part of Ruby's overall philosophy -- the focus is on
providing power to the programmer and secondarily on making the
language implementation simpler.
I am aware (as a result of reading what others have said and not from
experience), however, that this does make it harder to write the
interpreter, much less to write a Ruby compiler for a real or virtual
machine. I think this is one source of the tremendous feeling of
gratitude among Ruby users for matz's work.
>
> [snip]
>
> So what's a language implementor to do? You could have some sort of
> flag on
> strings indicating 'this is in a dictionary: no mutation'.
Or you could do what Ruby does (as elucidated by Dave Thomas in
previous posts).
> [snip]
Regards,
Mark
The Japanese language document is available through the RAA:
http://raa.ruby-lang.org/list.rhtml?name=rubytk-man
Regards,
Mark
> It's actually just a design choice that weighted, which would lead
> to shorter dev times in general: immutable or mutable strings. Guido
> thought it was the former.
That may be the case, but such a pragmatic, agnostic consideration
can't explain his words in the blog:
[...] (with the exception of Ruby's mutable strings, which I find an
abomination).
Gavin
"but for me the high point of the evening was Miguel de Icaza's
excitement over Python's feature which makes text files iterators
yielding the lines of the file in succession, so that you can write
for line in open(filename):
...process line... "
At which point I sighed.
Regards,
Mark
That's just Guido being Guido. I wouldn't particularly read too much
into it (at least technically) besides that.
--
Dan
--------------------------------------"it's like this"-------------------
Dan Sugalski even samurai
d...@sidhe.org have teddy bears and even
teddy bears get drunk
Wow! What an amazing feature! How could Guido have
come up with such a unique and novel idea, never seen before nor
since? :)
I am a big fan of File.foreach - but then I'm a big fan of the
blocks and iterators in general.
Actually, far from being impressed by the inclusion of this feature in
Python, I'm more surprised that Perl doesn't have it. To open a file
and iterate through its lines, I don't know of any Perl idiom that's
much simpler than the low-levelish open/read-loop/close sequence. I
think the closest you can get is something like this:
{
local @ARGV = ($filename);
while (<>)
{
...process $_...
}
}
. . . which saves the explicit close() line at the expense of legibility.
You could also save the close line by using an IO::File instance instead
of a normal filehandle:
{
my $fh = IO::File::->new("<$filename");
while (<$fh>)
{
...process $_...
}
}
But last I checked using IO::File really slowed things down.
Anyway. Back to Ruby.
:)
Yeah, and it's funny how he remarks about other languages allegedly
stealing features from Python but crediting CLU etc. instead!
Cheers,
Gavin
Hey, it could have been worse--you could have been sitting between
them when these great revelations were happening... :)
Er, that's because CLU and Icon *were* the inspiration for Python's
iterators, just as they were the inspiration for Ruby's. The PEP describing
generators (http://www.python.org/peps/pep-0255.html) references Sather and
Icon, and searching the archives of the python-iter list, I find no
references to Ruby at all.
--amk
You misunderstand me. I wasn't suggesting that Python or Ruby have
borrowed features from each other. What I was commenting on is the
following quote:
It was nice enough to compare the yield statements in Python and C#
(they are very similar, even though C# quotes CLU as the origin
rather than Python :-)
It seemed to me at first glance that Guido would like C# to credit
Python as the origin of the yield statement. Looking at the quote
again, I think I might have been a bit mischevous to suggest that.
Cheers,
Gavin
In message "Re: Question: immutable strings as design goal?"
on 03/08/19, Dan Sugalski <d...@sidhe.org> writes:
|Hey, it could have been worse--you could have been sitting between
|them when these great revelations were happening... :)
Yep. And it's indeed a great step in Python.
matz.
LOL!!!! So true, so true.
martin
eyes.roll
Actually, someone recently pointed out to me
(Gavin I think) that for/in is equivalent to
each, but he had wandered away from that since
he often needed each_with_index or something
similar.
So, then. How does Python's example work when
you need the index also? Oh, it can be done,
all right. Same as in Fortran.
For that matter, how do you do each_byte in
Python, to iterate a byte at a time?
This is not a flame. I don't know Python, and
I don't participate in language wars. But the
more I learn about Python, the less impressed
I am.
I certainly see no compelling reason for me to
switch from Ruby to Python. On the other hand,
it doesn't surprise me that they feel the same
way.
Hal
--
Hal Fulton
hal...@hypermetrics.com
Correct. It's well-known that Ruby's iterators
come from CLU -- I've never heard Icon cited,
but that could well be.
But I see no reason to think that *any* language
"stole from Python but credited CLU instead."
I did hear it asserted once that Python "stole"
iterators from Ruby. It's irrelevant to me. I'd
just as soon assume they came from Icon and CLU.
In message "Re: Question: immutable strings as design goal?"
on 03/08/20, "Hal E. Fulton" <hal...@hypermetrics.com> writes:
|So, then. How does Python's example work when
|you need the index also? Oh, it can be done,
|all right. Same as in Fortran.
There's enumerate().
a = [1,2,3]
for i,v in enumerate(a):
print i, v
matz.
Hm. Must be new in 2.3?
Traceback (most recent call last):
File "<stdin>", line 1, in ?
NameError: name 'enumerate' is not defined
>>>
-Mark
At Thu, 21 Aug 2003 23:34:13 +0900,
David Garamond wrote:
> Speaking of blog, I once read that Matz also keeps one. But Google can't
> find it for me. Any help?
But, of cource, in Japanese.
--
Nobu Nakada
Speaking of blog, I once read that Matz also keeps one. But Google can't
find it for me. Any help?
--
dave
Hrm...
Error: 500
Location: /error.jsp
Internal Servlet Error:
javax.servlet.ServletException
at org.apache.jasper.runtime.PageContextImpl.handlePageException(Unknown
Source)
at error_52._jspService(error_52.java(Compiled Code))
at org.apache.jasper.runtime.HttpJspBase.service(Unkn
..
Sometimes babelfish can translate Japanese text, but sometimes it
returns garbage (probably because of MIME type or charset issue?). In
this case it's the latter :-(
http://babelfish.altavista.com/babelfish/tr?lp=ja_en&url=http://www.rubyist.net/~matz/
Btw, "ruby-lang.org" and "rubyist.net" are registered by Matz.
"ruby-lang.net" is registered by someone in China. "ruby-lang.com",
surprisingly, is still available. :-)
--
dave
Try with excite.co.jp. In my experience, its translation is much better
(and works in this case :)
You might also like
--
_ _
| |__ __ _| |_ ___ _ __ ___ __ _ _ __
| '_ \ / _` | __/ __| '_ ` _ \ / _` | '_ \
| |_) | (_| | |_\__ \ | | | | | (_| | | | |
|_.__/ \__,_|\__|___/_| |_| |_|\__,_|_| |_|
Running Debian GNU/Linux Sid (unstable)
batsman dot geo at yahoo dot com
Try to remove the color-problem by restarting your computer several times.
-- Microsoft-Internet Explorer README.TXT