Чтение онлайн

на главную - закладки

Жанры

Программирование на языке Ruby
Шрифт:

Класс

Object
является корнем иерархии. Он предоставляет все методы, определенные во встроенном модуле
Kernel
.

Чтобы создать класс, наследующий другому классу, нужно поступить следующим образом:

class MyClass < OtherClass

 # ...

end

Помимо использования встроенных методов, вполне естественно определить и собственные либо переопределить унаследованные. Если определяемый метод имеет то же имя, что и существующий, то старый метод замещается. Если новый метод должен обратиться к замещенному им «родительскому» методу (так бывает часто), можно воспользоваться ключевым словом

super
.

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

Можно создавать синонимы методов. Для этого внутри определения класса предоставляется такой синтаксис:

alias newname oldname

Число параметров будет таким же, как для старого имени, и вызываться метод-синоним будет точно так же. Обратите внимание на отсутствие запятой;

alias
— это не имя метода, а ключевое слово. Существует метод с именем
alias_method
, который ведет себя аналогично, но в случае его применения параметры должны разделяться запятыми, как и для любого другого метода.

1.3.5. Методы и атрибуты

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

receiver.method
). Если имя метода является знаком препинания, то точка опускается. У методов могут быть аргументы:

Time.mktime(2000, "Aug", 24, 16, 0)

Поскольку каждое выражение возвращает значение, то вызовы методов могут сцепляться:

3.succ.to_s

/(x.z).*?(x.z).*?/.match("x1z_1a3_x2z_1b3_").to_a[1..3]

3+2.succ

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

nil
, а вызов любого метода от имени такого объекта приведет к ошибке. (Конечно,
nil
— полноценный объект, но он не обладает теми же методами, что и, например, массив.)

Некоторым методам можно передавать блоки. Это верно для всех итераторов — как встроенных, так и определенных пользователем. Блок обычно заключается в операторные скобки

do-end
или в фигурные скобки. Но он не рассматривается так же, как предшествующие ему параметры, если таковые существуют. Вот пример вызова метода
File.open
:

my_array.each do |x|

 some_action

end

File.open(filename) { |f| some_action }

Именованные параметры будут поддерживаться в последующих версиях Ruby, но на момент работы над этой книгой еще не поддерживались. В языке Python они называются ключевыми аргументами, сама идея восходит еще к языку Ada.

Методы могут принимать переменное число аргументов:

receiver.method(arg1, *more_args)

В данном случае вызванный метод трактует

more_args
как массив и обращается с ним, как с любым другим массивом. На самом деле звездочка в списке формальных параметров (перед последним или единственным параметром) может «свернуть» последовательность фактических параметров в массив:

def mymethod(a, b, *с)

 print a, b

 с.each do |x| print x end

end

mymethod(1,2,3,4,5,6,7)

# a=1, b=2, c=[3,4,5,6,7]

В Ruby есть возможность определять методы на уровне объекта (а не класса). Такие методы называются синглетными; они принадлежат одному-единственному объекту и не оказывают влияния ни на класс, ни на его суперклассы. Такая возможность может быть полезна, например, при разработке графических интерфейсов пользователя: чтобы определить действие кнопки, вы задаете синглетный метод для данной и только данной кнопки.

Вот пример определения синглетного метода для строкового объекта:

str = "Hello, world!"

str2 = "Goodbye!"

def str.spell

 self.split(/./).join("-")

end

str.spell # "H-e-l-l-o-,- -w-o-r-l-d-!"

str2.spell # Ошибка!

Имейте в виду, что метод определяется для объекта, а не для переменной. Теоретически с помощью синглетных методов можно было бы создать систему объектов на базе прототипов. Это менее распространенная форма ООП без классов [5] . Основной структурный механизм в ней состоит в конструировании нового объекта путем использования существующего в качестве образца; новый объект ведет себя как старый за исключением тех особенностей, которые были переопределены. Тем самым можно строить системы на основе прототипов, а не наследования. Хотя у нас нет опыта в этой области, мы полагаем, что создание такой системы позволило бы полнее раскрыть возможности Ruby.

5

Типичный пример — язык JavaScript (Прим. перев.)

1.4. Динамические аспекты Ruby

Ruby — динамический язык в том смысле, что объекты и классы можно изменять во время выполнения. Ruby позволяет конструировать и интерпретировать фрагменты кода в ходе выполнения статически написанной программы. В нем есть хитроумный API отражения, с помощью которого программа может получать информацию о себе самой. Это позволяет сравнительно легко создавать отладчики, профилировщики и другие подобные инструменты, а также применять нетривиальные способы кодирования.

Поделиться:
Популярные книги

Купеческая дочь замуж не желает

Шах Ольга
Фантастика:
фэнтези
6.89
рейтинг книги
Купеческая дочь замуж не желает

Стеллар. Заклинатель

Прокофьев Роман Юрьевич
3. Стеллар
Фантастика:
боевая фантастика
8.40
рейтинг книги
Стеллар. Заклинатель

Солнечный флот

Вайс Александр
4. Фронтир
Фантастика:
боевая фантастика
космическая фантастика
5.00
рейтинг книги
Солнечный флот

Изменяющий-Механик. Компиляция. Книги 1-18

Усманов Хайдарали
Собрание сочинений
Фантастика:
боевая фантастика
космическая фантастика
5.00
рейтинг книги
Изменяющий-Механик. Компиляция. Книги 1-18

Мастер 9

Чащин Валерий
9. Мастер
Фантастика:
боевая фантастика
попаданцы
технофэнтези
аниме
фэнтези
5.00
рейтинг книги
Мастер 9

Мечников. Избранник бога

Алмазов Игорь
5. Жизнь Лекаря с нуля
Фантастика:
альтернативная история
аниме
фэнтези
5.00
рейтинг книги
Мечников. Избранник бога

Дважды одаренный. Том II

Тарс Элиан
2. Дважды одаренный
Фантастика:
городское фэнтези
альтернативная история
аниме
5.00
рейтинг книги
Дважды одаренный. Том II

Император Пограничья 5

Астахов Евгений Евгеньевич
5. Император Пограничья
Фантастика:
аниме
фэнтези
фантастика: прочее
попаданцы
5.00
рейтинг книги
Император Пограничья 5

Лекарь Империи 5

Карелин Сергей Витальевич
5. Лекарь Империи
Фантастика:
городское фэнтези
аниме
героическая фантастика
попаданцы
5.00
рейтинг книги
Лекарь Империи 5

Убивать чтобы жить 5

Бор Жорж
5. УЧЖ
Фантастика:
боевая фантастика
космическая фантастика
рпг
5.00
рейтинг книги
Убивать чтобы жить 5

Лейтенант. Назад в СССР. Книга 8. Часть 1

Гаусс Максим
8. Второй шанс
Фантастика:
попаданцы
альтернативная история
5.00
рейтинг книги
Лейтенант. Назад в СССР. Книга 8. Часть 1

Кодекс Охотника. Книга IV

Винокуров Юрий
4. Кодекс Охотника
Фантастика:
фэнтези
попаданцы
аниме
5.00
рейтинг книги
Кодекс Охотника. Книга IV

Матабар

Клеванский Кирилл Сергеевич
1. Матабар
Фантастика:
фэнтези
5.00
рейтинг книги
Матабар

Адвокат Империи 2

Карелин Сергей Витальевич
2. Адвокат империи
Фантастика:
городское фэнтези
попаданцы
аниме
фэнтези
фантастика: прочее
5.00
рейтинг книги
Адвокат Империи 2