I would like to get the binary literal corresponding from a given integer, in this way:
4.to_literal
=> 0b100
Is there such to_literal method?
Use to_s with its optional base parameter to get a string.
4.to_s(2) #=> "100"
You can't get a literal as output.
Use String#% or Kernel#sprintf (%#b as format specifier):
'%#b' % 4
# => "0b100"
sprintf('%#b', 4)
# => "0b100"
Related
to_i returns 0 whenever the input starts by anything other than an integer. For example, if I input $32 it returns 0, but if I enter 32, it returns the number 32. I found another post that said to_i only accepts digits, but did not offer an alternative solution.
Is there a way around this? I want the user to be able to input a "$" before their number. As it stands, my code looks like this:
puts"What is the cost of a gallon of paint?"
cost=gets.chomp.to_i
total_cost=cost*#gallons_needed"
Meditate on these:
"$1\n"[1..-1].to_i # => 1
"$1.99\n"[1..-1].to_i # => 1
"$100.99\n"[1..-1].to_i # => 100
This breaks down when there's a leading -:
"-$100.99\n"[1..-1].to_i # => 0
That can be fixed using sub instead of a slice:
"-$100.99\n".sub('$', '').to_i # => -100
The problem is, money is not all integers, so to_i is probably not really what you want. Instead you should be using to_f:
"$1\n".sub('$', '').to_f # => 1.0
"$1.99\n".sub('$', '').to_f # => 1.99
"$100.99\n".sub('$', '').to_f # => 100.99
"-$100.99\n".sub('$', '').to_f # => -100.99
"$-100.99\n".sub('$', '').to_f # => -100.99
Note: It isn't necessary to use chomp to remove the trailing new-line. to_i and to_f will stop when they see a non-digit:
"1\n".to_i # => 1
"1.99\n".to_f # => 1.99
"1 1\n".to_i # => 1
"1.99 2\n".to_f # => 1.99
Again, because of this behavior, "\n" and 1\n or 2\n will be ignored.
String.to_i only parses the leading numeric characters in a string and stops as soon as it hits a non-numeric character. In this case, $ is non-numeric so you get 0.
This matches the behavior described in the documentation: Class: String (Ruby 2.0.0)
To properly parse the value, you'll need to strip the $ from the start of the input using something like:
cost = gets.chomp.sub('$','').to_i
In Ruby (PCRE), is it possible to use a backreference to a captured decimal value to define a repetition length?
/^(\d+),.{\1}/.match('4,abcdefgh') # Should match '4,abcd'
The above code just returns nil (finds no matches).
You can use String#to_i, which gives you the number at the start:
str = '4,abcdefgh'
str.match(/^(\d+),.{#{str.to_i}}/) # => #<MatchData "4,abcd" 1:"4">
No, you can't do that with regular expressions. If the range of decimal values however is limited, you could build a regular expression containing all possible combinations, something like:
'1abcde2abcde3abcde4abcde'.scan(/1.{1}|2.{2}|3.{3}|4.{4}/)
#=> ["1a", "2ab", "3abc", "4abcd"]
You could use two regular expressions:
str = '4,abcdefgh'
str =~ /\A(\d+,)/
str[0,$1.size+$1.to_i]
#=> "4,abcd"
How can we obtain formatted output using p function. of ruby.
I need to print a float with exactly two decimal places.
I want to do it using minimum characters so i want to use p function instead of puts and printf.
i have tried this
printf"%.2f",a.abs/2
Any idea on how to reduce characters ?
inspect is the method you need to override for p
class Float
def inspect
sprintf "%.2f", self
end
end
Result
p 12.0
#=> 12.00
Assuming you're ok about a string being returned, you can use use Kernel#sprintf
sprintf "%.2f", 1.234
=> "1.23"
Note that printf is really just sugar for IO.write(sprint()) so the above should be considered equiavelent.
You can use the method String#%
str % arg → new_str
Format—Uses str as a format specification, and returns the result of applying it to arg. If the format specification contains more than one substitution, then arg must be an Array or Hash containing the values to be substituted. See Kernel::sprintf for details of the format string.
In your example:
a = 5.3
p"%.2f"%a
If you use a formula you need additional braces:
p"%.2f"%(a.abs/2)
I need to print escaped characters to a binary file using Ruby. The main problem is that slashes need the whole byte to escape correctly, and I don't know/can't create the byte in such a way.
I am creating the hex value with, basically:
'\x' + char
Where char is some 'hex' value, such as 65. In hex, \x65 is the ASCII character 'e'.
Unfortunately, when I puts this sequence to the file, I end up with this:
\\x65
How do I create a hex string with the properly escaped value? I have tried a lot of things, involving single or double quotes, pack, unpack, multiple slashes, etc. I have tried so many different combinations that I feel as though I understand the problem less now then I did when I started.
How?
You may need to set binary mode on your file, and/or use putc.
File.open("foo.tmp", "w") do |f|
f.set_encoding(Encoding::BINARY) # set_encoding is Ruby 1.9
f.binmode # only useful on Windows
f.putc "e".hex
end
Hopefully this can give you some ideas even if you have Ruby <1.9.
Okay, if you want to create a string whose first byte
has the integer value 0x65, use Array#pack
irb> [0x65].pack('U')
#=> "e"
irb> "e"[0]
#=> 101
10110 = 6516, so this works.
If you want to create a literal string whose first byte is '\',
second is 'x', third is '6', and fourth is '5', then just use interpolation:
irb> "\\x#{65}"
#=> "\\x65"
irb> "\\x65".split('')
#=> ["\\", "x", "6", "5"]
If you have the hex value and you want to create a string containing the character corresponding to that hex value, you can do:
irb(main):002:0> '65'.hex.chr
=> "e"
Another option is to use Array#pack; this can be used if you need to convert a list of numbers to a single string:
irb(main):003:0> ['65'.hex].pack("C")
=> "e"
irb(main):004:0> ['66', '6f', '6f'].map {|x| x.hex}.pack("C*")
=> "foo"
In Ruby, trying to print out the individual elements of a String is giving me trouble. Instead of seeing each character, I'm seeing their ASCII values instead:
>> a = "0123"
=> "0123"
>> a[0]
=> 48
I've looked online but can't find any way to get the original "0" back out of it. I'm a little new to Ruby to I know it has to be something simple but I just can't seem to find it.
Or you can convert the integer to its character value:
a[0].chr
You want a[0,1] instead of a[0].
I believe this is changing in Ruby 1.9 such that "asdf"[2] yields "d" rather than the character code
To summarize:
This behavior will be going away in version 1.9, in which the character itself is returned, but in previous versions, trying to reference a single character of a string by its character position will return its character value (so "ABC"[2] returns 67)
There are a number of methods that return a range of characters from a string (see the Ruby docs on the String slice method) All of the following return "C":
"ABC"[2,1]
"ABC"[2..2]
"ABC".slice(2,1)
I find the range selector to be the easiest to read. Can anyone speak to whether it is less efficient?
#Chris,
That's just how [] and [,] are defined for the String class.
Check out the String API.
The [,] operator returns a string back to you, it is a substring operator, where as the [] operator returns the character which ruby treats as a number when printing it out.
I think each_char or chars describes better what you want.
irb(main):001:0> a = "0123"
=> "0123"
irb(main):002:0> Array(a.each_char)
=> ["0", "1", "2", "3"]
irb(main):003:0> puts Array(a.each_char)
0
1
2
3
=> nil