Для каждого... break

Я чувствую себя грязным каждый раз, когда я "ломаюсь" из каждой конструкции (PHP/Javascript)

Так что-то вроде этого:

//Пример Javascript

for (object in objectList)
{
   if (object.test == true)
   {
      //do some process on object
      break;
   }

}

Для больших объектных списков я бы смог выстроить более элегантное решение. Но для небольших списков нет заметной проблемы с производительностью, и поэтому "почему бы и нет"? Это быстро и, что более важно, легко понять и следовать.

Но он просто "чувствует себя не так". Вид вроде утверждения goto.

Как вы справляетесь с такой ситуацией?

Ответ 1

Я использую перерыв. Это идеальное решение.

Ответ 2

Это быстро и, что важнее, легко понять и следовать.

Не чувствуй себя плохо в перерыве. Goto неодобрительно, потому что это быстро и важнее не просто понять и следовать.

Ответ 3

Видишь, перерыв меня совсем не пугает. Программирование построено на goto, а for-break - как и все структуры управления - это просто специальная форма goto, предназначенная для улучшения читаемости вашего кода. Никогда не плохо себя чувствуешь в написании читаемого кода!

Теперь я do чувствую себя грязным относительно прямых сравнений с true, особенно при использовании оператора равенства преобразования типов... О да. То, что вы написали - if (object.test == true) - эквивалентно написанию if (object.test), но требует больше мысли. Если вы действительно хотите, чтобы сравнение было успешным только в том случае, если object.test является как логическим значением, так и true, вы должны использовать оператор строгого равенства (===)... В противном случае пропустите его.

Ответ 4

Для небольших списков нет никаких проблем с этим. Как вы упомянули, вы можете подумать о более "элегантном" решении для больших списков (особенно списки с неизвестными размерами).

Иногда это кажется неправильным, но все в порядке. Вы научитесь любить break вовремя.

Ответ 5

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

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

Ответ 6

Я думаю, что читать легче и, следовательно, легче поддерживать.

Ответ 7

Он должен быть таким. Break предназначен для выпрыгивания из цикла. Если вы нашли то, что вам нужно в цикле, почему нужно продолжать цикл?

Ответ 8

Разрывы и продолжения не являются доступными. Они там не просто так. Как только вы закончите с структурой цикла, выйдите из цикла.

Теперь, что бы я избежал, очень, очень глубокое гнездование (a.k.a. дизайн антистатика стрелки).

if (someCondition)
{
    for (thing in collection)
    {
        if (someOtherCondition)
        {
            break;
        }
    }
}

Если вы собираетесь сделать перерыв, убедитесь, что вы структурируете свой код, чтобы он был только на одном уровне. Используйте вызовы функций, чтобы сохранить итерацию как можно более мелкой.

if (someCondition)
{
    loopThroughCollection(collection);
}

function loopThroughCollection(collection)
{
    for (thing in collection)
    {
        if (someOtherCondition)
        {
            doSomethingToObject(thing);
            break;
        }
    }
}

function doSomethingToObject(thing)
{
    // etc.
}

Ответ 9

Я действительно не вижу ничего неправильного в выходе из цикла for. Если у вас нет какой-либо хеш-таблицы, словарь, в котором у вас есть какой-то ключ для получения значения, на самом деле нет другого пути.

Ответ 10

Я бы использовал оператор break.

Ответ 11

В общем, нет ничего плохого в инструкции break. Однако ваш код может стать проблемой, если такие блоки появятся в разных местах вашей базы кода. В этом случае операторы break представляют собой код, маленький для дублированного кода.

Вы можете легко извлечь поиск в функцию многократного использования:

function findFirst(objectList, test)
{
  for (var key in objectList) {
    var value = objectList[key];
    if (test(value)) return value;
  }
  return null;
}

var first = findFirst(objectList, function(object) {
  return object.test == true;
}
if (first) {
  //do some process on object
}

Если вы всегда обрабатываете найденный элемент каким-либо образом, вы также можете упростить свой код:

function processFirstMatch(objectList, test, processor) {
  var first = findFirst(objectList, test);
  if (first) processor(first);
}

processFirst(
  objectList,
  function(object) {
    return object.test == true;
  },
  function(object) {
    //do some process on object
  }
}

Таким образом, вы можете использовать возможности функциональных возможностей JavaScript, чтобы сделать ваш оригинальный код более выразительным. В качестве побочного эффекта это приведет к выведению выражения break из вашей обычной базы кода в вспомогательную функцию.

Ответ 12

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

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

for (object in objectList)
{
  //do some process on object
}

Таким образом, если вам нужно выполнить этот процесс более чем на одном элементе, ваш код не сломается (каламбур).

Ответ 13

Мое предпочтение - просто использовать break. Это быстро и обычно не усложняет ситуацию.

Если вы используете цикл for, while или do while, вы можете использовать переменную, чтобы определить, продолжать или нет:

for ($i = 0, $c = true; ($i < 10) && $c; $i++) {
    // do stuff

    if ($condition) {
        $c= false;
    }
}

Единственный способ выйти из цикла foreach - break или return.

Ответ 14

Используйте

Object object;
int index = 0;

do
{
    object = objectList[index];
    index++;
}
while (object.test == false)

если нарушение от цикла for заставляет вас чувствовать себя неловко.