Упростить типичную (?) Условную конструкцию - PullRequest
0 голосов
/ 23 октября 2018

Я часто видел (и иногда писал сам) конструкции вроде:

if(A || B)
{
    var sharedValue = ...;
    if(A)
    {
      // do stuff with sharedValue
    }
    else
    {
      // do other stuff with sharedValue 
    }
}

Реальный пример:

switch (e.Key)
{
   /* 
    * Don't mind the switch, since it can be simply converted into:
    * if(e.Key == Key.Left || e.Key == Key.Right) { ... }
    */
   case Key.Left: 
   case Key.Right:
       var container = containerFromData(data);
       if (e.Key == Key.Left)
       {
          this.TryNavigateBackward(container);
       }
       else
       {
          this.TryNavigateForward(container);
       }
}

Я действительно чувствую как будто я скучаючто-то, поэтому должен быть лучший (более простой, менее многословный) способ описать это, но не смог придумать идею.Этот вопрос может быть несколько связан с языком программирования одноразового использования (я в настоящее время на C #), но есть ли какие-либо конструкции, способные упростить данный пример?

Примечание: Мне известен троичный условный оператор a ? b : c, но это (по крайней мере, в C #) работает только при извлечении значений и их помещении в переменные.В приведенном выше примере мы хотим сделать разные (возможно сложные) вещи с общим значением .

1 Ответ

0 голосов
/ 26 октября 2018

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

Во-первых, если ООП находится на столе, наследование может представлятьэтот вид общего поведения.Что бы вы сделали, это инкапсулировали общее, A -специфичное и B -специфичное поведение в классах Shared, ASpecific и BSpecific, где ASpecific и BSpecific наследуются от Shared.Затем, если либо A, либо B, вы раскручиваете экземпляр либо ASpecific, либо BSpecific соответственно, а затем обрабатываете его как экземпляр Shared.Если у вас есть условия C, D и т. Д., Которые не используют совместно используемую вещь, возможно, у вас был бы другой родительский класс с именем Base, и вы бы CBase, DBase наследовали от Base, Shared наследуя от Base, и раскрутите экземпляр в зависимости от условия и обработайте результат как экземпляр Base.

Во-вторых, вы можете использовать инверсию управления, передаваяА-специфичное и В-специфичное поведение для совместно используемого метода, когда требуется общий контент.Вы можете использовать ООП для этого или чисто функционального программирования.Если перейти ко второму (поскольку первое похоже на приведенное выше решение и, возможно, не так хорошо), у вас будет функция shared, которая принимает функцию f в качестве аргумента.Функция f будет иметь сигнатуру, которая требует передачи общего объекта. Затем, если A, вызовите shared с функцией (указатель или анонимный inline), которая выполняет специфические для A вещи для общего ресурса.объект перешел в него;в противном случае, если B, вызовите shared с функцией, которая делает специфичные для B вещи для общего объекта, переданного в него.

Если все, что вы действительно хотите избежать, это вложение, вы также можетевывести содержимое if (A || B) { … } и сделать его доступным для общего доступа, который объявлен, но не создан в более широком контексте;затем, позже, проверьте A и B отдельно и знайте, что в этих случаях shared будет иметь требуемую настройку ранее.

...