2009-08-06 3 views
5

Рассмотрим следующий надуманный пример:Stylistic вопрос о возвращении недействительным

void HandleThat() { ... } 

void HandleThis() 
{ 
    if (That) return HandleThat(); 
    ... 
} 

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

Как правило, я бы ожидал увидеть:

if (That) {HandleThat(); return;} 

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

SO community, могу ли я узнать ваше мнение о том, является ли стиль кодирования возвращающего-пустоты путаным или проблематичным? У этого есть чувство идиомы; следует ли использовать это или избегать?

Обычно я стремился к ясности и использовал второй стиль. С другой стороны, в первой форме есть аккуратность, которая немного меня привлекает.

+0

В случае, если это имеет какой-либо интерес, мое фактическое использование этого - поручить родительскому классу при определенных обстоятельствах. Viz: void производный класс :: f (...) {if (залог) возвращает parentclass :: f (...); ...} –

ответ

13

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

Возвращаясь из функции прототипированной пустоты, она должна быть возвращена;

+0

+1 Я не вижу веских причин, почему кто-то должен использовать первое соглашение при возвращении пустоты. – Eric

+0

Согласен, последний более интуитивно понятен и читабельен - определенно стоит пара дополнительных персонажей. – Amber

+1

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

11

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

return HandleThat(); 

с типом возвращаемого аннулируются и выяснить одаренность, прежде чем они на самом деле понять код. Когда вы делаете больше, чем одну вещь в ветке if/else, вам действительно нужно использовать фигурные скобки и поместить шаги в разные строки. Занимает больше места, но его легче понять:

if (That) { 
    HandleThat(); 
    return; 
} 
3

Никогда не видел этого раньше.

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

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

4

Правила языка C говорят, что если функция, объявленная как возвращающая void, пытается вернуть выражение, выражение не будет оцениваться.

http://c0x.coding-guidelines.com/6.8.6.4.html

+0

Оба стиля генерируют одинаковые результаты. Для этого кода: void a() {printf ("World! \ N");} void b() {printf ("Hello"); return a(); } вы получите Hello World, как ожидалось. –

+1

Я проверял, что с полной оптимизацией и удалением с помощью GCC 4.0 –

+0

Я думаю, что это неопределенное поведение технически. – sylvanaar

2

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

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

Смежные вопросы