Превращение длинного фиксированного числа в массив Ruby
Есть ли способ в ruby, чтобы включить fixnum, как 74239
в массив, как [7,4,2,3,9]
?
6 ответов
Вам не нужно совершать путешествие туда-обратно по суше для такого рода вещей:
def digits(n)
Math.log10(n).floor.downto(0).map { |i| (n / 10**i) % 10 }
end
ary = digits(74239)
# [7, 4, 2, 3, 9]
Это предполагает, что n
положительно, конечно, поскользнуться n = n.abs
в смеси могут позаботиться об этом, если это необходимо. Если вам нужно охватить неположительные значения, то:
def digits(n)
return [0] if(n == 0)
if(n < 0)
neg = true
n = n.abs
end
a = Math.log10(n).floor.downto(0).map { |i| (n / 10**i) % 10 }
a[0] *= -1 if(neg)
a
end
Возможно, не самое элегантное решение:
74239.to_s.split('').map(&:to_i)
Выход:
[7, 4, 2, 3, 9]
Начиная с Ruby 2.4, целые числа ( FixNum
отсутствует в 2.4+) есть встроенныйdigits
метод, который извлекает их в массив их цифр:
74239.digits
=> [9, 3, 2, 4, 7]
Если вы хотите сохранить порядок цифр, просто объедините reverse
:
74239.digits.reverse
=> [7, 4, 2, 3, 9]
Документы: https://ruby-doc.org/core-2.4.0/Integer.html
Метод divmod может использоваться для извлечения цифр по одной за раз
def digits n
n= n.abs
[].tap do |result|
while n > 0
n,digit = n.divmod 10
result.unshift digit
end
end
end
Быстрый тест показал, что это быстрее, чем использование журнала для определения количества цифр раньше времени, что само по себе быстрее, чем строковые методы.
bmbm(5) do |x|
x.report('string') {10000.times {digits_s(rand(1000000000))}}
x.report('divmod') {10000.times {digits_divmod(rand(1000000000))}}
x.report('log') {10000.times {digits(rand(1000000000))}}
end
#=>
user system total real
string 0.120000 0.000000 0.120000 ( 0.126119)
divmod 0.030000 0.000000 0.030000 ( 0.023148)
log 0.040000 0.000000 0.040000 ( 0.045285)
Вы можете преобразовать в строку и использовать метод chars:
74239.to_s.chars.map(&:to_i)
Выход:
[7, 4, 2, 3, 9]
Это немного элегантнее, чем разделение.
Вы также можете использовать Array.new
вместо map
:
n = 74239
s = Math.log10(n).to_i + 1 # Gets the size of n
Array.new(s) { d = n % 10; n = n / 10; d }.reverse