From: Wesley J Landaker Date: 2003-06-26T22:31:57+09:00 Subject: Re: String#split(' ') and whitespace (perl user's surprise) On Thursday 26 June 2003 6:14 am, Mike Stok wrote: > I have to confess that I use a lot of Perl, and some of its idioms > are deeply embedded in my mind. > > Im the course of parsing some data in Ruby I used a fragment of code > like > > rules.each_line do |rule| > sku, price, special = rule.chomp.split(' ', 3) > # [...] > end > > where rules was composed of lines of the form > > A 50 3 for 130 > > coming from a perl background I would have expected 'A', '50' and '3 > for 130' to have been assigned to sku, price and special. As it > turned out special had leading whitespace. > > Maybe this is the difference Hal alludes to in From Perl to Ruby in > his book The Ruby Way: "Also, note that split also behaves slightly > differently." > > Is this intentional behaviour? I think that the Perl behaviour is > more useful (that is trimming the leading whitespace off the limit-th > element returned.) I don't know if it's intentional or not, but I do see the following at http://www.rubycentral.com/book/ref_c_string.html#String.split split str.split( pattern=$;, [ limit ] ) -> anArray Divides str into substrings based on a delimiter, returning an array of these substrings. If pattern is a String, then its contents are used as the delimiter when splitting str. If pattern is a single space, str is split on whitespace, with leading whitespace and runs of contiguous whitespace characters ignored. And they have an example: " now's the time".split(' ') 損 ["now's", "the", "time"] This seems to imply that split(' ', 3) ought to work like you were expecting. A little testing with irb seems to show that this behaves differently any time the "limit" argument is given. In fact, when a regex matching whitespace is given, you get an extra empty entry at the front; this is another possible problem, but maybe is correct since it's not the "magic" single space parameter which is said to trim leading whitespace. See below: $ cat test.rb str = " A 50 3 for 130" p str.split p str.split(' ') p str.split(' ',3) p str.split(/\s+/) p str.split(/\s+/,3) $ ./ruby -v test.rb ruby 1.8.0 (2003-05-31) [i686-linux] ["A", "50", "3", "for", "130"] ["A", "50", "3", "for", "130"] ["A", "50", " 3 for 130"] <-- this differs from what is documented ["", "A", "50", "3", "for", "130"] ["", "A", "50 3 for 130"] This seems like a ruby bug: limit seems to be counting whitespace characters and not whitespace "runs" when ' ' is given as the pattern. But maybe it's a documentation bug. Who knows? -- Wesley J. Landaker - wjl@icecavern.net OpenPGP FP: C99E DF40 54F6 B625 FD48 B509 A3DE 8D79 541F F830