Подтверждение типа параметра Ruby

Исходя из фона Java, я немного обеспокоен Ruby полностью blasé отношением к его параметрам метода. В то время как в Java я мог гарантировать, что параметр x является типом, необходимым для правильной работы метода, в Ruby у меня нет способа гарантировать, что x является целым числом, строкой или чем-то еще в этом отношении.

Пример: если бы я хотел написать метод absolute_value в Java, заголовок был бы похож на

public static int absoluteValue(int x)

В Ruby это будет что-то вроде

def self.absolute_value(x)

В этом примере, в коде Java, я могу быть абсолютно уверен, что передаваемый параметр не является "С Днем Рождения!" но в коде Ruby я этого не знаю. Как предотвратить эту ситуацию в Ruby, чтобы код не врезался в Runtime?

5 ответов

Привет, добро пожаловать в Руби. Я тоже работал на Java за последние годы, и я действительно любил Java в то время.

Теперь, не правильно думать о Ruby как об отсутствии проверки типов. Он имеет, по меньшей мере, такую ​​же проверку типов, как и Java, но только эти типы могут меняться, поэтому проверки выполняются во время выполнения.

Плюс ко всему, этот дробящий шаблон объявления на старых языках раздражает. Приложение, проверенное типом, которое не может быть завершено вовремя, чтобы быть полезным, ничего хорошего не имеет. Программа с проверкой типа, которая слишком многозначительна для чтения, скорее всего, станет устаревшей.

И если тип не проверяется при первом запуске вашей программы Ruby, он может быть покрыт вашими тестами.

Но если вы не протестируете его, вы не знаете, работает ли он в любом случае, поэтому абстрактные знания, которые соответствуют типам вызовов метода, не будут столь же полезными, как вы могли бы себе представить.

В любом случае Ruby в этом смысле хорошо себя зарекомендовал как язык. Как реальная платформа, у RoR есть некоторые проблемы с производительностью, как в скорости, так и в использовании памяти, но я не знаю ни одного проекта, жалующегося на динамическую типизацию, и желая, чтобы они проваливались через получение RSI с некоторым старым подробным языком.


Добро пожаловать в Руби, Квас. Надеюсь, вы научитесь любить печатать утки. Вы получаете уверенность в своем коде в Ruby, написав тесты, не завися от проверки типов и компиляции. Вы получаете скорость, гибкость и удобочитаемость, не определяя типы.


Пойдем со мной, если ты хочешь жить.

a="String"
puts a.kind_of? Integer # false
puts a.kind_of? String # true
a=10
puts a.kind_of? Integer # true
puts a.kind_of? String # false


Ruby (почти?) всегда интерпретируется, поэтому проверка типа, указанная в заголовке метода, в любом случае будет сбой во время выполнения. " duck typing" поведение (где тип операции проверяет, имеет ли объект, на который действует данный метод), является частью идиомы Ruby, и вы не должны пытаться писать Java в Ruby. Научитесь писать Ruby-код вместо этого.


Вы можете выполнить минимальный уровень тестирования метода, сохраняя при этом утиную печать. Чтобы использовать пример из книги "Язык программирования рубина"

def +(other)
 raise TypeError, "Point-like argument expected" unless other.respond_to? :x and other.respond_to? :y
 Point.new(@x + other.x, @y + other.y)
end

Этот пример используется для реализации операции "+" в классе Point, которая работает с (x, y) пуринами. Вместо того, чтобы делать other.is_a? (Point) - они протестировали реализованный метод, который для меня кажется хорошим вариантом. Можно утверждать, что "другой" объект может иметь x и y attrs, что означает что-то другое, что, хотя правильный аргумент пропустит тот факт, что я просто указываю на середину. Мой подход также наклонен к тому, чтобы делать добавление напрямую и терпеть неудачу, если кто-то проходит неправильный тип.

licensed under cc by-sa 3.0 with attribution.