You are here: Forums Ask a Rails expert Ruby oddity...
Posted in Forums : Ask a Rails expert
System Admin Sign in to rate this post |
Anyone care to comment on this Ruby oddity. What am I missing here? irb(main):001:0> x = “01” |
Authority 62
Posting Rating 100
Sign in to rate this post
|
Honestly, I have no idea. But I guess it could have something to do with the fact that the maximum value for a signed integer with only one byte is +/- 7 (0111 = +7, 1111 = -7 … if I remember binary correctly). |
Authority 25
Posting Rating 99
Sign in to rate this post
|
By starting the number with a leading zero, when Ruby typecasts the string to an integer, it is doing so as an octal. 08 is not a valid octal number, hence the error. |
System Admin Sign in to rate this post |
Ernie, thanks for that. Next (obvious) question is why? Wouldn’t decimal have been a more sensible choice? |
Authority 25
Posting Rating 99
Sign in to rate this post
|
It’s not Ruby-specific. A lot of dynamically typed interpreted languages allow for alternate representations of integers for convenience. Common shorthand for octal is a leading zero, while hexadecimal can be done with a preceding “0x”. |
System Admin Sign in to rate this post |
Using 0x for hex makes some sense and using something similar for Octal would also make sense. But to not default to decimal just seems daft to me. As a programmer, how many times have you converted a string to an integer and wanted it treated as octal, rather than decimal? |
Authority 50
Posting Rating 0
Sign in to rate this post
|
Hey David, how many times does a programmer have a string like “08” that he needs to convert to an integer to format it? Apparently String#% does an Integer(“08”) internally which is a little more restrictive about valid integer values than String#to_i is. The original printf format strings however expect a decimal value if you supply a %d and as Ruby is a dynamic language, If you find some time, it would be interesting to see this on the Ruby mailing list. Cheers Pascal |
Authority 25
Posting Rating 99
Sign in to rate this post
|
David, But that’s just it—you didn’t convert it to an integer when you passed it as an argument, you told sprintf to do that for you. Using String#to_i was the solution if you wanted to manage the conversion yourself. The “0x” and “0” for hexadecimal and octal integer representations have been around for ages, it’s just one of those things to get used to, as it’s nearly universal across programming languages, and you’re certainly not the first to get bitten by it. As Pascal pointed out, String#to_i behaves differently than a straight Integer cast does. This is because String#to_i takes an optional base parameter, defaulting to 10, and has additional logic to support varying bases. I disagree with Pascal that it makes sense to handle the assume the argument for the %d conversion is a decimal number on the right hand side, though—a big portion of what sprintf is designed to do is do on-the-fly format conversions of an integer to different string representations. Because of this, it’s a perfectly valid expectation to pass in an Integer in octal format and request it in decimal in the output. The best policy is always to pass the value in as an Integer, not as a string, to avoid any ambiguity. |
Ask a Rails expert : copy to clipboard
Ask a Rails expert : API call problem
Ask a Rails expert : Invoke a plugin from a plugin?
Ask a Rails expert : Restful problem
Ask a Rails expert : Problem with form for ActiveResource model
Ask a Rails expert : Paypal(How to set u/p)
Ask a Rails expert : MySQL for Production?
Ask a Rails expert : Git for Windows