- Структура каталогов Ruby проекта
- Подключение файлов с помощью require
- Модули в Ruby
- Методы класса и модуля (статические методы)
- Блоки в Ruby
Мы уже научились использовать методы Ruby Core API и Ruby Std-lib API. Пришла пора познакомиться с API одной из наиболее распространённых библиотек ActiveSupport. Данная библиотека поставляется вместе с Rails, но также может быть использована независимо от Rails. Библиотека ActiveSupport как и Rails, как и любая другая библиотека является Гемом (Gem). Gem - это общее название для всех библиотек Ruby, которые могут быть установлены через встроенный в Ruby менеджер пакетов RubyGems. Таким образом, для того чтобы установить ActiveSupport необходимо выполнить команду:
gem install activesupport
ActiveSupport содержит множество полезных возможностей, расширяющих возможность Ruby и его ядра. Поскольку ActiveSupport является частью Rails, документация находится здесь: http://api.rubyonrails.org. Чтобы найти информацию непосредственно по ActiveSupport, откройте каталог file
(сразу под строкой поиска), затем каталог activesupport
. Файл README.rdoc
содержит общие сведения, остальная документация сосредоточена в отдельных файлах.
Если присмотреться к структуре каталогов ActiveSupport то можно заметить что библиотека имеет модульную структуру. Например, расширения классов ядра Ruby находятся в каталоге core_ext
. К слову, название каталога core_ext
является соглашением для расположения файлов с расширениями ядра языка. То есть, если мы хотим добавить метод в класс String
или Array
, лучше всего создать в проекте каталог core_ext
и в нём - 2 файла: string.rb
и array.rb
:
dice_game
├── README.md
└── lib
├── core_ext
│ ├── array.rb
│ └── string.rb
├── dice_game
│ ├── dice.rb
│ └── game.rb
└── dice_game.rb
Тогда сразу ясно, что в коде есть методы, расщиряющие ядро и понятно в каких файлах они определяются.
Такая структура каталогов ActiveSupport хороша тем, что позволяет нам подключать не всю библиотеку, а только те её части которые нам нужны. Например, если мы хотим использовать в проекте только расширения для класса Array
, то используем такой вызов:
require 'active_support/core_ext/array'
После этого нам станут доступны все методы класса Array
, определённые в ActiveSupport. Они располагаются в каталоге activesupport/lib/active_support/core_ext/array
. Обратите внимание что здесь каталог называется activesupport
, а главный файл active_support.rb
, то есть между именами есть различие в символе нижнего подчёркивания. Такое иногда встречается, и это не критично.
Чтобы подключить всю библиотеку используем вызов:
require 'active_support/all'
Вооружившись Гемом ActiveSupport, испробуем его в деле. Найдём методы, расширяющий ядро Ruby:
Для класса Hash
:
- Метод, превращающий хэш в объект класса
ActiveSupport::HashWithIndifferentAccess
. Такой объект ничем не отличается от хэша, однако если ключом пары является строка, вы можете использовать символ (объект классаSymbol
) и наоборот:
fruits[:apple] # => 7
fruits['apple'] # => 7
-
Метод, возвращающий хэш без пар, ключи которых были переданы в качестве аргументов метода
-
Метод, превращающий хэш в строку запроса (query string)
-
Метод, превращающий все ключи хэша в объекты класса
String
Для класса Array
:
-
Метод, возвращающий пустой хэш, если последний элемент массива не является хэшем и последний элемент массива в обратном случае
-
Метод, принимающий один аргумент и если этот аргумент является массивом, то он возвращается без изменений. В ином случае возвращается массив единственным элементом которого будет переданный аргумент
-
Метод, возвращающий последние несколько элементов массива, начиная с индекса переданного в качестве аргумента
Помните о системе соглашений Ruby. Если вы испытаете затруднения с поиском метода, пропробуйте спросить себя: "Если бы я был этим методом, как бы я назывался?"
Совершите рефакторинг проекта Игра в «Кости». Для этого вынесите логику обработки хода в отдельный класс Turn
. Создайте у него метод resolve
, чтобы вычисление хода игры выглядело так:
# Метод new должен принимать необходимые для вычисления хода аргументы
Turn.new().resolve
Напишите метод my_each
, расширяющий класс Array
, который работает точь-в-точь как и метод each
:
numbers = [1, 2, 3, 4, 5]
numbers.each { |element| puts element }
# => 1
# => 2
# => 3
# => 4
# => 5
numbers.my_each { |element| puts element }
# Результат вывода будет такой же как в предыдущем случае
Предметная область:
-
У нас есть объект класса
Mothership
, обладающий способностью вычислять координаты для сверхсветового прыжка (методcompute
) -
Есть второй класс
Ship
, объекты которого управляют истребителем и могут совершать сверхсветовой прыжок, но не в состоянии произвести расчет координат
Задача:
- С помощью блока реализуйте метод
jump
для объектов классаShip
который в момент вызова будет вызывать методMothership#compute
и таким образом устанавливать координаты для прыжка
Предварительное определение классов располагается в исходном коде проекта jump
.
- GeekBrains
- Электронная почта:
[email protected]
- Slack канал