LINUX.ORG.RU

do ... while - аргументы за и против


0

0

Никак не могу понять, почему некоторые разработчики придерживаются стиля написания C-шных программ, исключающего конструкции do {...} while () ? Всю жизнь пользовался repeat ... until на Паскале. И здесь я в недоумении. Поясните, пожалуйста.
Чем while() {...} "правильнее" ? :)

★★★★★

Это стёб такой?

Когда, что надо в конкретном, то и применяй...

Практика показывает, что while(){...} чаще нужен, чем do{...}while(), а если ты всегда применяешь do{...}while(), то скорее всего это недоработки в алгоритмах

golodranez ★★★★
()
Ответ на: комментарий от golodranez

> Это стёб такой?

Это вполне конкретный вопрос.
Я столкнулся с таким ограничением на применение циклов в одном из технических
документов и до сих пор в недоумении. Не понимаю зачем в стандарте кода запрещать
do {} while(); Про goto нам еще в школе рассказывали, а с этим столкнулся
впервые.
Сейчас пороюсь по конкретным примерам ...
/* Value.c */
int main (int argc, char **argv) {
    unsigned int i1;
    unsigned int i2;
    i1 = 0;
    do {
        i2 = i1++;
    } while (i2<i1);
    printf("MAX_UINT: %u\n",i2);
    return 0;
}
Вроде ничего ничитабельного нет ?

pacify ★★★★★
() автор топика

>Чем while() {...} "правильнее" ? :)

Для танкистов:

do-while - делаем, потом проверяем - всегда 1 раз провернётся

while - проверяем, надо ли, и только потом делаем

Это как передний привод и задний привод в машине зимой по укатанному снегу: когда знаешь, что делать, то любой привод контролируем.

Так что сранивать их глупо...

Если же do-while запрещён какими-либо стандартами то тока в целях защититься от дурака-программера.

Pi ★★★★★
()
Ответ на: комментарий от Pi

> Если же do-while запрещён какими-либо стандартами то тока в целях защититься от дурака-программера.

Во - четкий и ясный ответ. Вопрос закрыт.

pacify ★★★★★
() автор топика
Ответ на: комментарий от pacify

>Во - четкий и ясный ответ. Вопрос закрыт.

но если постараться вспомнить, кгда последний раз приходилось использовать do-while, то почему-то вспоминается первый курс, информатика, совершенно ускусственное задание по переписыванию циклов одного типа другими :D вообще-то do-while полезен тока если нада что-либо сделать и переспросить у юзера, не повторить ли - в остольном этот цикл неестественен.

Pi ★★★★★
()
Ответ на: комментарий от Pi

еще, как вариант его применения:

#define something(x) do { \
                         //blah-blah \
                         //blah-blah \
                     } while(0);

Здесь do-while как раз используется для защиты от тупых программеров.
Хотя, как вариант, вместо do-while просто фигурные скобки.

eXire ★★
()
Ответ на: комментарий от Pi

Похоже на то. Сейчас еще раз порылся по архивам. Встретил do/while пару раз в своих исходниках, пару раз в чужих. Ну, еще пару раз repeat/until в обработчиках событий от мыши/клавиатуры. А так в большинстве своем действительно, циклы с пост-условием встречаются редко.

pacify ★★★★★
() автор топика
Ответ на: комментарий от eXire

>Хотя, как вариант, вместо do-while просто фигурные скобки.

Как вариант - это хорошо, конечно. Вот только уверены ли вы, что любой стандарт С (или приземленнее - компилятор) допускает фигурные скобки от балды в коде?

anonymous
()
Ответ на: комментарий от pacify

А я, помню, вот буквально в прошлом месяце его применял. Один раз. :)

Teak ★★★★★
()
Ответ на: комментарий от anonymous

Это не фигурные скобки от балды, а блок (он же составной оператор). Допустим везде, где допустим любой другой вид оператора. Да, в любом компиляторе.

Teak ★★★★★
()
Ответ на: комментарий от eXire

во первых ; в конце макроопределения лишняя.

> Хотя, как вариант, вместо do-while просто фигурные скобки.

нет. do-while защищает от случая когда тот кто использует something(x) поставит в конце ;

if (...) something(x); else something(y);

вариант с do-while здесь сработает, а просто фигурные скобки нет

dilmah ★★★★★
()
Ответ на: комментарий от eXire

> еще, как вариант его применения:
> 
> #define something(x) do { \
>                         //blah-blah \
>                         //blah-blah \
>                     } while(0);

Здесь завершающее ';' - грубейшая ошибка, сводящая смысл использования 
такой конструкции к 0.

Правильные варианты: 

#define something(x) do { \
                         //blah-blah \
                         //blah-blah \
                     } while(0)

или

#define something(x) if (1) { Всякая чушь } else

anonymous
()

пример do...while:

do {
ret = select(0, NULL, NULL, NULL, &req);
} while (ret < 0 && errno == EINTR);

по-моему удобно.
это надо запрещать?! бред.

anonymous
()
Ответ на: комментарий от Teak

>Это не фигурные скобки от балды, а блок (он же составной оператор). >Допустим везде, где допустим любой другой вид оператора. Да, в любом >компиляторе.

Да, похоже ты прав. Во всяком случае мне пока не удалось найти компилятор, который на это ругнулся. Мне казалось, что по аналогии с паскалем некоторые стандарты/реализации С не допускают использования, "{}" помимо как после конструкций вроде if/do/while/etc.

anonymous
()
Ответ на: комментарий от anonymous

А вот это уже опасно.

> #define something(x) if (1) { Всякая чушь } else

может привести к

something(x) /* ; нету */ Всякая чушь

так что do{ }while(0) наше всё.

k_andy ★★★
()
Ответ на: комментарий от anonymous

> пример do...while:
>
> do {
> ret = select(0, NULL, NULL, NULL, &req);
> } while (ret < 0 && errno == EINTR);
>
> по-моему удобно.

заменяется однострочником:
while ((ret = select(0, NULL, NULL, NULL, &req)) < 0 && errno == EINTR);

anonymous2 ★★★★★
()
Ответ на: комментарий от anonymous2

Это с какой-то стороны опасный оператор по простой причине: слово "do"
очень маленькое, его легко забыть поставить, а компилятор не ругнётся на 

{
   // do domething
} while(condition);

Разумеется, эта конструкция будет иметь совершенно другую сементику, чем

do {
   // do domething
} while(condition);

jek_
()
Ответ на: комментарий от jek_

Не могу себе представить такую ошибку. По-моему, это из области фантастики.

Teak ★★★★★
()

широко применяю данную конструкцию в расчетах при коррекции исходных данных

do {
        method();
} while(correct());

anonymous
()

Если у человека было написано что вроде:

код;

еще код;

while(тыр-пыр 8 дыр){

тот же самый код;

}

почему бы не использовать do...while ?

Запрещать цикл с пост условием - это маразм!!!

Tima-S

anonymous
()
Ответ на: комментарий от anonymous

> Не могу себе представить такую ошибку. По-моему, это из области фантастики.

У некоторых мания писать фигурные скобки под именем оператора, вот так:

// a very useful comment
while(cond)
{
}

и 

// a very useful comment
do
{
} while(bla-bla);

или 

// a very useful comment
do
{
}
while(bla-bla);

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

И ага -- потом фиг найдёшь ошибку.

jek_
()
Ответ на: комментарий от jek_

> У некоторых мания писать фигурные скобки под именем оператора

Бедные больные люди, вот всё что я могу сказать. Создают себе проблему на ровном месте. Да, им помогло бы новое ключевое слово для циклов с постусловием, спору нет, но ещё больше им помогло бы вправление мозгов на место (или прекращение практики оплаты за количество строк :)).

Teak ★★★★★
()

Чисто субъективно - do { } while несколько сложнее читается. Даже не знаю, почему.

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

Второй момент (тоже субъективный), сам цикл работает не "единообразно". В while(<условие>) { <код> } - есть четкая связь между текущим значением <условия> (учитывая текущие значения переменных) и <кодом> (т.е <условие> -> <код>). И часто это может мысленно восприниматься как реализация абстракции вида map, reduce, и.т.д. А в do { <код> } while(<условие>) такой простой связи между кодом и условием в моем мозгу не образуется, в нем первый раз <код> не привязан к <условию> вообще

WFrag ★★★★
()
Ответ на: комментарий от WFrag

Так он первый раз и не привязан к условию. Первый раз он выполняется в любом случае, а потом уже, если надо, повторяется ещё раз. По-моему вполне удачный синтаксис, и порядок правильный.

Teak ★★★★★
()
Ответ на: комментарий от Teak

>Так он первый раз и не привязан к условию.

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

WFrag ★★★★
()
Ответ на: комментарий от WFrag

Честно говоря не понимаю. Контекст один и тот же, ничего не меняется, что тут явно выражать?

Может тебе вообще идея цикла с постусловием не нравится как таковая, с не синтаксис do..while?

Teak ★★★★★
()
Ответ на: комментарий от Teak

Всё нормально, я даже goto использую, но очень редко - когда без него совсем никак :)

frame ★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.