PHP: создание метода псевдосоединения внутри объекта

StackOverflow https://stackoverflow.com/questions/642582

  •  22-07-2019
  •  | 
  •  

Вопрос

Я пытаюсь создать объект, способный обрабатывать условные операторы, подобные запросам. Поэтому я могу «соединить» два условия вместе, чтобы создать зависимость между ними в зависимости от типа используемого «соединения». В настоящее время у меня есть простой объект, который содержит следующие методы:

public function addCondition ( Condition $condition, $join = null )
{
    $this->conditions[] = $condition;
}

public function validate ( )
{
    foreach ( $this->conditions as $condition )
    {
        $result = $condition->validate( );
        [...]
    }
}

Проблема в том, что мне нужно иметь возможность выполнить условное соединение между двумя операторами, что повлияет на возвращаемое значение метода validate. Идея состоит в том, что вы могли бы поставить условие следующим образом:

$this->addCondition($condition_1);
$this->addCondition($condition_2, 'AND');
$this->addCondition($condition_3, 'NOT');

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

В этом примере скажем:

condition_1 = Apple is Red
condition_2 = Apple is Ripe
condition_3 = Apple is Golden Delicious

Используя это, я должен предположить, что если бы я пропустил спелое, красное и золотистое вкусное яблоко, результат validate () был бы ложным. Метод должен завершиться сбоем, потому что 'join' для condition_3 - это НЕ.

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

Любая помощь очень ценится! Спасибо.

Это было полезно?

Решение

Поместите логику в ваши подклассы Условие.

Создайте класс Condition_And, который принимает два (или более) объекта Condition и возвращает true, только если они оба имеют значение true.

Создайте класс Condition_Or, который принимает два (или более) объекта Condition и возвращает false, если любой из них равен true.

Создайте класс Condition_Not, если считаете, что это необходимо (Apple НЕ является Golden Delicious).

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

Другие советы

Условия, которые включают как И , так и ИЛИ , по сути являются вложенными. У вашего класса, кажется, нет способа выразить это.

Отсутствие вложения означает, что все ваши условия должны быть либо объединены с помощью AND , либо все должны быть объединены с помощью OR . В любом случае - вы не можете использовать оба одновременно.

Для вашего примера AND кажется естественным выбором, поэтому все, что вам нужно, это флаг NOT для каждого условия:

$this->addCondition($condition_1, true);   // e.g.: must be true to succeed
$this->addCondition($condition_2, true);
$this->addCondition($condition_3, false);  // e.g.: must be false to succeed

Затем вы бы сделали:

$valid = true;

foreach ( $this->conditions as $condition )
{
  $valid = $valid && $condition->validate();
  if (!$valid) 
  {
    // react to "validation failed at $condition"
  }
}

return $valid;
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top