Я строю стохастические имитационные модели.Переходы между состояниями обрабатываются методами событий, но порядок их возникновения зависит от случайности событий, поэтому мне нужна некоторая форма динамической отправки.Вот уже более десяти лет это прекрасно работает для меня в Ruby с использованием send
, но меня привлекает скорость Crystal, поэтому я пытаюсь создать каркас для построения симуляций в кристаллическом режиме.
Природа моделей заключается в том, что методы событий инициируют определенные подмножества других событий на основе случайных условий (и после случайных временных задержек, но я это охватил), поэтому события действительно должны быть идентифицированы читаемым пользователем тегом некоторыхсортировать для целей планирования.Я выбрал подход использования Hash
, который отображает идентификаторы событий на соответствующие им Proc
s, но хочу отделить логику модели от вызова события, как в следующем классе и модуле «модель».(Пожалуйста, имейте в виду, что реальный код будет более сложным, чем этот, с методами событий, которые планируют последующие события со случайными задержками через очередь приоритетов. Это подразумевается как MCVE только для аспекта проблемы с динамической отправкой по имени.)
Модель:
require "./my_module"
class UserClass
include MyModule
def initialize
@method_set = {
:m1 => ->m1,
:m2 => ->m2,
:m3 => ->m3
}
p methods
end
def m1
puts "In method1"
end
def m2
puts "In method2"
end
def m3
puts "In method3"
end
end
UserClass.new.run(5)
Выполнение логики управления, которая является общей для всех моделей:
module MyModule
# would like to replace this with a macro that
# automates construction of the hash of procs.
macro methods
{{ @type.methods.map &.name.stringify }}
end
@method_set = {} of Symbol => Proc(Nil)
def run(iterations)
keys = @method_set.keys
iterations.times { @method_set[keys[rand(keys.size)]].call }
end
end
Теперь перейдем к актуальному вопросу.В серьезных моделях могут быть десятки или сотни методов событий, поэтому я хотел бы использовать макросы для автоматизации построения Hash
.Я провел некоторое исследование и нашел, как получить имена методов с помощью макроса, но не могу найти правильное заклинание, чтобы выкашлять Symbol
-привод Hash
, подобное тому, которое я создаю вручную в конструкторе.Буду признателен за любую помощь или предложения для альтернативных подходов.