Эти бесконечные если отчетность плохая картина?


Я только спрашиваю, потому что практически весь базовый код, который я унаследовал здесь, в C# и PHP, выглядит так:

if (varOne == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varTwo == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varThree == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varFour == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varFive == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varSix == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varSeven == flag) {
    run_some_sql();
    set_some_flag = true;
}

if (varEight == flag) {
    run_some_sql();
    set_some_flag = true;
}

Около десяти тысяч строк.

Я не сошла с ума, верно? Разве это плохо? Есть только пять петель в весь базовый код около 50 000 строк.

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

Я полностью потерял рассудок? Восемь человек работали над этим до меня, и я всерьез волнуюсь. Есть ли хорошая причина, чтобы делать такого рода вещи?



651
9
задан 7 апреля 2011 в 07:04 Источник Поделиться
Комментарии
3 ответа

Это плохо. Очень плохо.

Похоже, оригинальный реализатор не совсем понимаю массивы. Вы обязательно должны выполнить рефакторинг этого. Майкл К. ответ был правильный подход. В синтаксис c#:

// Hopefully these variables are already in an array or list already, otherwise:
MyType[] myVariables = new MyType[] { varOne, varTwo, /* ... */ varEight };

foreach (MyType variable in myVariables)
{
if (variable == flag)
{
run_some_sql();
set_some_flag = true;
}
}

Обратите внимание, что если run_some_sql() только должна быть выполнена один раз, вы можете выйти раньше и сэкономить время вычислений:

foreach (MyType variable in myVariables)
{
if (variable == flag)
{
run_some_sql();
set_some_flag = true;

break;
}
}

Если это тот случай, когда вам нужно только выполнить run_some_sql() один раз, вы можете сделать код еще проще с помощью новой технологии LINQ синтаксис:

if (myVariables.Any(v => v == flag))
{
run_some_sql();
set_some_flag = true;
}

Во время рефакторинга, я также рекомендую выбрать какой лучше имена переменных, чем Вароне, varTwo, флаги т. д. Хотя я предполагаю, что это просто ваши примеры. :)

12
ответ дан 7 апреля 2011 в 08:04 Источник Поделиться

Нет, вы не потеряли свой ум. Он должен больше нравится...

// declared and set somewhere
flags = new int[x];

//...

for (int value: flags) {
if (value == flag) {
run_some_sql();
set_some_flag = true;
}
}

...полагая, что флаги того же типа и они действительно делают то же самое. Вы уверены, что там нет Бога, где-то объекты, что другие методы основывая свои ответы выкл?

10
ответ дан 7 апреля 2011 в 07:04 Источник Поделиться

Другой возможный подход, чтобы сохранить SQL в словарь и использовать флаг в качестве ключа

Dictionary<TypeOfFlag, string> dict = new Dictionary<TypeOfFlag, string>();
dict.Add(valueOne, "SELECT x FROM y");
dict.Add(valueTwo, "SELECT z FROM t");
...

string sql;
if (dict.TryGetValue(flag, out sql)) {
RunSQL(sql);
set_some_flag();
}

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

Словари имеют постоянную времени порядка O(1) и не требуют петли для того, чтобы доступ к элементу и, конечно, требует не бесконечны, если заявления!


Бесконечные если-цепи и переключатель-заявления (дело-отчетность на другие языки) часто сильный намек на то, что плохой процедурный подход был использован. Применение сухих принципе может даже улучшить такие процедурные подходы. Полиморфизм (субтипы)- объектно-ориентированный подход, который можно часто устранить эти неприятные структур.

5
ответ дан 16 марта 2014 в 10:03 Источник Поделиться