I finally figured out that it was the Plus sign right next to the
“bar”, after the “to_s” method that Ruby dislikes. If I insert a
space, I get the correct output. If I take out both spaces, I get the
correct output. It’s only if there’s a space after the “to_s” and none
between the Plus sign and string-in-quotes that it blows up.
That is:
puts ‘foo’ + x.to_s + ‘bar’ # this works
puts ‘foo’ + x.to_s +‘bar’ # doesn’t work
puts ‘foo’ + x.to_s+ ‘bar’ # this works
puts ‘foo’ + x.to_s+‘bar’ # this works
Anyone know why this might be? I haven’t played with it anymore, so I
wonder if this bug exists with other methods.
I suspect that having no space after the + makes Ruby think it is a
unary operator. And since to_s is a method, Ruby thinks that you’re
passing +‘bar’ to x.to_s. This can’t be the only problem, though,
since it is giving you a SyntaxError before it actually complains about
passing an unexpected argument to to_s…
I suspect that having no space after the + makes Ruby think it is a
unary operator. And since to_s is a method, Ruby thinks that you’re
passing +‘bar’ to x.to_s. This can’t be the only problem, though,
since it is giving you a SyntaxError before it actually complains about
passing an unexpected argument to to_s…
I think it’s trying to parse as
puts(‘foo’ + x.to_s, +‘bar’)
where the comma is missing. So it thinks +‘bar’ is not an argument to
to_s but to puts.
Thanks for the feedback Robert. I didn’t know Ruby could do that.
I’ll just try to be more consistent with spaces and plus signs to avoid
this problem again.
it may be parsing as ‘foo’ + x.to_s(+‘bar’) since to_s can sometimes
take an argument.
This makes sense. When translating the infix notation to method usage
(don’t
know if this will be done by the interpreter), the first step is
‘foo’ + x.to_s +‘bar’ => ‘foo’.+(x.to_s +‘bar’)
“String#+” has one argument, so “x.to_s +‘bar’” must be one argument.
When
looking to “x” it is not clear for the interpreter, what the result of
“x.to_s”
will be, but it knows, that “to_s” has an (optional) argument.
So it tries to find “String#+@” method for ‘bar’ and fails.
The possibility to backtrack after failure and try first to evaluate
“x.to_s”,
which returns the string “‘1’”, an then to compute “‘1’ +‘bar’” (works
without
any problem) will not be done due to good reasons for the general case.
Wolfgang Nádasi-Donner
This forum is not affiliated to the Ruby language, Ruby on Rails framework, nor any Ruby applications discussed here.