Самая элегантная петлевая конструкция? - PullRequest
8 голосов
/ 17 ноября 2008

Извините за новый вопрос. Я все еще учусь программированию. Поэтому я использую C ++, и мне нужно сделать что-то вроде этого:

int n;
do {
    n = get_data();
    if(n != -1)
        send(n);
} while(n != -1);

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

Ответы [ 10 ]

19 голосов
/ 17 ноября 2008
int n;
while (-1 != (n = get_data())) {
    send(n);
} // while
17 голосов
/ 17 ноября 2008

Аналогично eed3si9n, но, возможно, легче читать:

 int n;
 while (n = get_data(), n != -1)
 {
     send(n);
 }
15 голосов
/ 17 ноября 2008

Как насчет использования перерыв :

int n;
while(1) {
    n = get_data();
    if(n == -1)
        break;
    send(n);
}

Таким образом, вы тестируете только один раз и немедленно выходите, если get_data не возвращает желаемого.

11 голосов
/ 17 ноября 2008
for (int n = get_data(); n != -1; n = get_data()) {
  send(n);
}
4 голосов
/ 17 ноября 2008

Ваша оригинальная версия в порядке.

В моей последней работе по программированию на С мы должны были следовать стандартам кодирования MISRA.

В соответствии с правилами MISRA это:

int n;
while(1) {
    n = get_data();
    if(n == -1)
        break;
    send(n);
}

запрещено из-за break, а это:

while((n = get_data()) != -1) { send(n); }

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

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

int n;
bool valid;
do {
    n = get_data();
    valid = n != -1;
    if(valid)
        send(n);
} while(valid);

Но для такого простого теста, как "n != -1", возможно, не стоит делать программу длиннее.

2 голосов
/ 25 марта 2011
/* This is cleaner */ 
AGAIN:;
    int n = get_data();
    if (n != -1)
    {
        send(n);
        goto AGAIN;
    }


/* This has some charm as well */ 
int n;
while ((n = get_data()) != -1)
    send(n);
/* and now i see that this is the top answer.  Oh well */ 
1 голос
/ 18 ноября 2008
int n;
n = get_data();
while (n != -1) {
  send(n);
  n = get_data();
}
0 голосов
/ 23 февраля 2010

В Python вы бы сделали это:

while True:
    n = get_data()
    if n == -1:
        break
    send(n)

Как видите, это не намного короче, чем ваша версия на Си. Обычно код Python в 5-10 раз меньше своего эквивалента на Си. Это не тот случай, поэтому вы можете наслаждаться читаемым, достаточно коротким, быстрым фрагментом и сосредоточиться на чем-то другом.

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

0 голосов
/ 18 ноября 2008
int get_data()
{
 ...
}

void _send(int )
{
 ...
}

int  send(int (*a) ())
{
   int n = a();

   if (n == -1)
      return n;

   _send(n);
   return 1;
}

int main()
{
  int (*fp)();
  fp = get_data;
  while ( send(fp)!= -1 );

  return 0;
}

НТН

0 голосов
/ 18 ноября 2008

Построить с goto:)

int n;
goto inside; do {
  send(n);
inside:
  n=get_data();
} while(n!=-1);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...