How to replace a letter with a corresponding number

I am working through the Ruby Q. website and I am already stuck on
number 1 - Solitaire Cypher.

I have a string, let’s say “RUBYC ODEIS THEBE STXXX”. I need to convert
each letter to its corresponding number (i.e., A=1, B=2, etc.).

I had hoped I could use gsub with a regexp like this:

coded_text = text.gsub(/[A-Z/,[1-26])

but that doesn’t work. Any ideas?

Hello,

You can do this task in steps below:

  1. Create a hash contains character as key and its corresponding number
    as
    value.
  2. Use String#split to split the String into an array.
  3. Use Array#collect to convert characters to corresponding number.

Example:

    # Create hash contains alphabetical table
    alpha_table = {}
    (('A'..'Z').zip(1..26)).each { |x| alpha_table[x[0]] = x[1] }

    s = "RUBYC" # String to convert
    result = s.to_a.collect { |x| alpha_table[x] }

On Wed, May 23, 2012 at 7:22 PM, Rich McMullen [email protected]
wrote:

but that doesn’t work. Any ideas?


Posted via http://www.ruby-forum.com/.

Regards,

1 Like

Hi,

I’m sorry, the last command must be:

result = s.split('').collect { |x| alpha_table[x] }
1 Like

On Wed, May 23, 2012 at 2:22 PM, Rich McMullen [email protected]
wrote:

but that doesn’t work. Any ideas?
First of all you need to know if you have a formula to calculate the
corresponding number or you need a mapping.
In this case, each letter’s ASCII value can be used:

1.9.2p290 :005 > "A".ord
 => 65

so for example, if you substract 64 from the ord of a char, you will
get 1 for A, 2 for B, etc.
Now for gsub to work you can use the block form, in which you will get
the matched part of the string, and the result of the block is the
replacement and try this:

text.gsub(/[A-Z]/) {|m| m.ord - 64}

1.9.2p290 :007 > text = "ABCDE"
 => "ABCDE"
1.9.2p290 :008 > text.gsub(/[A-Z]/) {|m| m.ord - 64}
 => "12345"

Hope this helps,

Jesus.

Awesome! Thanks guys, I appreciate it.

On Wed, May 23, 2012 at 8:22 PM, Rich McMullen [email protected]
wrote:

coded_text = text.gsub(/[A-Z/,[1-26])

try

>s=("A".."Z").to_a.join
=> "ABCDEFGHIJKLMNOPQRSTUVWXYZ"

0> text="ABCDE"
=> "ABCDE"

> text.gsub(/[A-Z]/){|c|s.index(c)+1}
=> "12345"

Just to add something here…

You can use a Hash as a function (which if you think about it, all mapping structure is a function by definition):

result = s.split('').collect(&:alpha_table)
1 Like

i think you can make a small function for this replacement. :smiley: :blush: