Подтвердить что ты не робот

Разница между целым (значение) и значением .to_i

Для такого строкового объекта:

twohundred = "200"

В чем разница между выполнением:

Integer(twohundred)  #=> 200

и

twohundred.to_i      #=> 200

Есть ли разница? Рекомендуется ли использовать один из них?

4b9b3361

Ответ 1

Integer(num) будет генерировать исключение ArgumentError, если num не является допустимым целым числом (вы можете указать базу).

num.to_i будет конвертировать столько, сколько может.

Например:

"2hi".to_i 
#=> 2

Integer("2hi")
#=> throws ArgumentError

"hi".to_i
#=> 0

Integer("hi")
#=> throws ArgumentError

"2.0".to_i
#=> 2

Integer("2.0")
#=> throws ArgumentError

Ответ 2

Из документа Ruby для Integer():

Целое число (arg, base = 0) → integer... Если arg является String, когда база опущена или равна нулю, radix индикаторы (0, 0b и 0x). В любом случае, строки должны быть строго соответствует числовому представлению. Это поведение отличается от строки String # to_i.

Другими словами, Integer("0x100") => 256 и "0x100".to_i => 0.

Ответ 3

Давайте рассмотрим различия между использованием метода экземпляра String # to_i и метода модуля Kernel:: Integer. Во-первых, пусть встраивается позже в другой метод int1:

def int1(str)
  Integer(str) rescue nil
end

Таким образом, если str не может быть истолковано как целое число, Integer приведет к возникновению исключения ArgumentError, в результате чего возвращается в строку nil. Если Integer не вызывает выполнение, то int вернет целочисленный эквивалент строки.

Чтобы завершить сравнение, добавьте регулярное выражение, которое подтверждает, что содержимое строки представляет целое число перед использованием to_i для преобразования.

R = /
    (?<=\A|\s) # match beginning of string or whitespace character (positive lookbehind)
    -?         # optionally match a minus sign
    \d+        # match one or more digits
    (?=\s|\z)   # match whitespace character or end of string (positive lookahead)
    /x         # free spacing regex definition mode

def int2(str)
  str =~ R ? str.to_i : nil
end

Как и в случае int1, если str не может быть истолковано как целое число, int2 вернет nil; else, int возвращает целочисленный эквивалент строки.

Попробуйте несколько сравнений.

str = '3'
str.to_i       #=> 3 
int1(str)      #=> 3 
int2(str)      #=> 3

str = '-3'
str.to_i       #=> -3 
int1(str)      #=> -3 
int2(str)      #=> -3

str = '3.0'
str.to_i       #=> 3 
int1(str)      #=> nil 
int2(str)      #=> nil 

str = '3.2'
str.to_i       #=> 3 
int1(str)      #=> nil 
int2(str)      #=> nil 

1e3            #=> 1000.0
str = '1e3'
str.to_i       #=> 1 
int1(str)      #=> nil 
int2(str)      #=> nil 

str = '-1e3'
str.to_i       #=> -1 
int1(str)      #=> nil 
int2(str)      #=> nil 

str = '- 1e3'
str.to_i       #=> 0 
int1(str)      #=> nil 
int2(str)      #=> nil 

str = '3a'
str.to_i       #=> 3 
int1(str)      #=> nil 
int2(str)      #=> nil 

str = '1-3a'
str.to_i       #=> 1
int1(str)      #=> nil 
int2(str)      #=> nil

str = 'b3'
str.to_i       #=> 0
int1(str)      #=> nil 
int2(str)      #=> nil

Строка # to_i считывает цифры (возможно, предшествует знак минуса), пока не будет прочитана пробельная символика или не будет до конца строки. Затем он просто преобразует эти цифры и возможный знак минус в Fixnum, который он возвращает. to_i имеет свои применения, но эти примеры показывают, что вы должны использовать int1 или int2, если вы хотите вернуть nil, если строка не содержит представления целого числа.