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

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

Жанры

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

WarnLow.new(ticker, 90)

WarnHigh.new(ticker, 110)

puts 'Нажмите [return] для завершения.'

gets

Модуль

DRbUndumped
(см. листинге 20.3) следует включать в любой объект, который не нужно подвергать маршалингу. Самого присутствия этого модуля в числе предков объекта достаточно, чтобы
drb
не пытался применять к нему маршалинг. Вот исходный текст этого
модуля целиком:

module DrbUndumped

def _dump(dummy)

raise TypeError, "can't dump"

end

end

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

20.3. Rinda: пространство кортежей в Ruby

Термин «пространство кортежей» появился в 1985 году, а сама идея еще старше. Кортежем называется массив или вектор, состоящий из элементов данных (как строка в таблице базы данных). Пространство кортежей — это большое объектное пространство, наполненное кортежами, нечто вроде «информационного супа».

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

Первой реализацией пространства кортежей был проект Linda — исследование в области параллельного программирования, выполненное в Йельском университете в 1980-х годах. Реализация на языке Ruby (конечно, на основе библиотеки

drb
), естественно, называется Rinda.

Кортеж в Rinda может быть массивом или хэшем. На хэш налагается дополнительное ограничение: все ключи должны быть строками. Вот несколько примеров простых кортежей:

t1 = [:add, 5, 9]

t2 = [:name, :add_service, Adder.new, nil]

t3 = { 'type' => 'add', 'value_1' => 5, 'value_2' => 9 }

Элемент кортежа может быть произвольным объектом; это работает, потому что

drb
умеет выполнять маршалинг и демаршалинг объектов Ruby. (Конечно, необходимо либо включить модуль
DRbUndumped
, либо сделать определения объектов доступными серверу.)

Пространство объектов создается методом

new
:

require 'rinda/tuplespace'

ts = Rinda::TupleSpace.new

# ...

Поэтому сервер выглядит так:

require 'rinda/tuplespace'

ts = Rinda::TupleSpace.new

DRb.start_service("druby://somehost:9000", ts)

gets #
Нажать Enter для завершения сервера.

А клиент — так:

require 'rinda/tuplespace'

DRb.start_service

ts = DRbObject.new(nil, "druby://somehost:9000")

# ...

К пространству кортежей в Rinda применимы пять операций:

read
,
read_all
,
write
,
take
и
notify
.

Операция чтения

read
позволяет получить один кортеж. Но способ идентификации кортежа не вполне очевиден: необходимо задать кортеж, соответствующий искомому; при этом
nil
соответствует любому значению.

t1 = ts.read [:Sum,nil] # Может извлечь, например, [:Sum, 14].

Обычно операция

read
блокирует выполнение программы (для синхронизации). Чтобы быстро проверить существование кортежа, можно выполнить неблокирующее чтение, задав нулевой тайм-аут:

t2 = ts.read [:Result,nil],0 # Возбуждает исключение, если кортеж

# не существует.

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

read_all
, который возвращает массив:

tuples = ts.read_all [:Foo, nil, nil]

tuples.each do |t|

# ...

end

Метод

read_all
не принимает второго параметра. Он всегда блокирует программу, если не найдено ни одного подходящего кортежа.

Операция

take
— это чтение, за которым следует удаление. Иными словами, метод
take
удаляет кортеж из пространства кортежей и возвращает его вызывающей программе:

t = ts.take [:Sum, nil] # Кортежа больше нет в пространстве кортежей.

Может возникнуть вопрос, почему не существует явного способа удаления. Надо полагать, что этой цели служит метод take.

Метод

write
помещает кортеж в пространство кортежей. Второй параметр показывает, сколько секунд кортеж может существовать, прежде чем система сочтет, что срок его хранения истек. (По умолчанию его значение равно
nil
, то есть срок хранения не ограничен.)

ts.write [:Add, 5, 9] # Хранить "вечно".

ts.write [:Foo, "Bar"], 10 # Хранить 10 секунд.

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

Солнце мертвых

Атеев Алексей Григорьевич
Фантастика:
ужасы и мистика
9.31
рейтинг книги
Солнце мертвых

Герда

Веркин Эдуард Николаевич
Детские:
детская проза
5.00
рейтинг книги
Герда

Путь Шедара

Кораблев Родион
4. Другая сторона
Фантастика:
боевая фантастика
6.83
рейтинг книги
Путь Шедара

Третий. Том 2

INDIGO
2. Отпуск
Фантастика:
космическая фантастика
попаданцы
5.00
рейтинг книги
Третий. Том 2

Вольный Лекарь. Ученик. Трилогия

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

Ермолов

Гордин Яков Аркадьевич
1373. Жизнь замечательных людей
Документальная литература:
биографии и мемуары
5.00
рейтинг книги
Ермолов

Зов Атлантиды

Риддл А. Дж.
3. Тайна происхождения
Фантастика:
научная фантастика
альтернативная история
7.62
рейтинг книги
Зов Атлантиды

День греха

Браун Сандра
Любовные романы:
остросюжетные любовные романы
9.03
рейтинг книги
День греха

Неучтенный элемент. Том 5

NikL
5. Антимаг. Вне системы
Фантастика:
фэнтези
5.00
рейтинг книги
Неучтенный элемент. Том 5

Время зимы

Субботина Айя
Фантастика:
фэнтези
4.00
рейтинг книги
Время зимы

Ворон

LizaMoloko
Фантастика:
попаданцы
фэнтези
гаремник
5.00
рейтинг книги
Ворон

Этьен и его тень

Воробьев Евгений Захарович
Приключения:
прочие приключения
5.00
рейтинг книги
Этьен и его тень

Гримуар темного лорда V

Грехов Тимофей
5. Гримуар темного лорда
Фантастика:
попаданцы
аниме
фэнтези
5.50
рейтинг книги
Гримуар темного лорда V

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

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