Как я могу одновременно отправить метод нескольким экземплярам, ​​если раньше он отправлялся только одному? - PullRequest
1 голос
/ 25 мая 2011

В моем гипотетическом приложении пользователи могут задавать вопросы, на которые затем отвечает Oracle. Вы можете использовать метод Predictor.predictor, чтобы получить соответствующий Oracle, которому вы сможете направить свои вопросы. Когда вы #ask задаете вопрос, вы получите ответ вместе с уверенностью Oracle (число с плавающей запятой в диапазоне 0..1) относительно его ответа.

class BaseOracle; def ask(question); ...; end; end
class UnreliableOracle < BaseOracle; ...; end

module Predictor
  def self.predictor
    @predictor ||= UnreliableOracle.new
  end
end

Predictor.predictor.ask("How many fingers am I holding up?")
 # => ["three fingers", 0.2]

В этой реализации вы каждый раз получаете один и тот же Oracle, экземпляр UnreliableOracle. Я хотел бы изменить реализацию Predictor.predictor таким образом, чтобы методы, вызываемые на нем, были делегированы в коллекцию Oracle, некоторые из которых лучше других. Другими словами, я хочу, чтобы это работало примерно так:

class BaseOracle; ...; end
class UnreliableOracle < BaseOracle; ...; end
class PopCultureOracle < BaseOracle; ...; end
class ScienceOracle < BaseOracle; ...; end
class LiteraryOracle < BaseOracle; ...; end
class FingerCountingOracle < BaseOracle; ...; end

module Predictor
  def self.predictor
    ############## What goes here?
  end
end

# This actually asks several oracles for an answer and picks the best one.
Predictor.predictor.ask("How many fingers am I holding up?")
 # => ["four fingers", 1.0]

Какой лучший способ сделать это?

1 Ответ

2 голосов
/ 25 мая 2011

Это, по сути, шаблон разработки стратегии , где каждый Oracle фактически является стратегией для ответа на вопросы.

Самый простой (и, возможно, самый чистый) подход заключается в создании MetaOracle, который спрашивает других оракулов, какой правильный ответ, и выбирает лучший ответ:

class MetaOracle
  def oracles
    @oracles ||= [ScienceOracle.new, LiteraryOracle.new, # ...
  end

  def ask(question)
    oracles.map { |o| o.ask question }.        # Ask each Oracle a question ...
      sort_by { |answer| -answer.certainty }.  # sort by the best answers ...
      first                                    # ... and pick the best one.
  end
end

module Predictor
  def self.predictor
    @predictor ||= MetaOracle.new
  end
end

Теперь Оракул с лучшим ответом победит и будет тем ответом, который вы видите.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...