Stepan Parunashvili
Stepan Parunashvili

Reputation: 2845

Why does 0 return on this ruby base conversion method

as part of a ruby challenge, I'm making a custom method num_to_s(num,base) which takes a number and base, and returns a string with the new base.

The question gave me the hint that you can find the value of each digit by this operation --

(123 / 10**0) % 10 == 3 # ones place
(123 / 10**1) % 10 == 2 # tens place
(123 / 10**2) % 10 == 1 # hundreds place

So, I created the following function --

def num_to_s(num, base) 
    values =  ["0", "1", "2","3","4","5","6","7","8","9","a","b","c","d","e","f"]

    answer_array = []

    highest_power = 0 

    #find the highest power
    while base**highest_power <= num
        highest_power+=1
    end

    current_power = 0 
    #run a loop to find the values for base**0 to the highest power
    while current_power <= highest_power
        digit = values[ ((num / base**current_power) % base) ]

        answer_array << digit
        current_power +=1
    end
    answer_array.reverse.join


end

num_to_s(4,2)
num_to_s(20,16)

When I run this function, everything works great, except sometimes the answer is prefixed by 0. If I were to remove the 0 though, the answer would be correct.

Just out of curiuosity, why does the 0 show up in the method?

Example --

num_to_s(5,2) #=> 0101

While the actual answer is 101

Upvotes: 0

Views: 105

Answers (2)

Borodin
Borodin

Reputation: 126742

You may be interested in this solution. It uses a constant array Symbols to avoid reassigning the array values every time the method is called. It also makes use of Numeric#divmod, which returns the quotient and the remainder of a division in one operation.

Symbols =  ('0' .. '9').to_a + ('a' .. 'z').to_a

def num_to_s(num, base)

  ret = ''

  while num > 0 or ret == ''
    num, digit = num.divmod(base)
    ret = Symbols[digit] + ret
  end

  ret

end

puts num_to_s(4, 2)
puts num_to_s(20, 16)
puts num_to_s(255, 8)
puts num_to_s(44_027, 36)

output

100
14
377
xyz

Upvotes: 1

Save
Save

Reputation: 11938

while current_power <= highest_power

this is the problem. You look for the first power of the base higher than num, that means you don't have to consider such power: in your example, highest_power is 3, that means, if you allow current_power to be equal to it, you get 4 iterations {0,1,2,3}, while you only need 3, namely {0,1,2}.

Replace it with

while current_power < highest_power

and you should be fine. The strange part is that you say "sometime" you get a 0, while, in theory, you should get it every single time.

Upvotes: 2

Related Questions