Можно ли опустить фигурные скобки в Java? [закрыто]


83

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

Как бы то ни было, у меня вопрос: в чем важность скобок? Ничего страшного, если я их опущу? Пример:

for (int i = 0; i < size; i++)  {
   a += b;
}

против

for (int i = 0; i < size; i++)
   a += b;

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


Я всегда использую средство форматирования кода для удобства чтения, поскольку оно устраняет множество потенциальных причин путаницы. Это может сделать использование фигурных скобок излишним
— Питер Лоури,

Ответы:


148

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

for (int i = 0; i < size; i++)
   a += b;
   System.out.println("foo");

что означает это:

for (int i = 0; i < size; i++)
   a += b;
System.out.println("foo");

... но это должно было быть так:

for (int i = 0; i < size; i++) {
   a += b;
   System.out.println("foo");
}

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

Соглашения о кодировании в каждой компании, в которой я работал, требовали этого - это не означает, что у некоторых других компаний нет других соглашений ...

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


12
@vedran: Значит, вы знаете об этой проблеме, но думаете, что она вас никогда не укусит? И что каждый, читающий ваш код, будет знать, чего ожидать? Я просто говорю - есть причина, по которой они требуются в соглашениях о кодировании, с которыми я работал :)
— Джон Скит

12
Я просто чувствовал себя частным, с кем свысока разговаривает сержант. Да, хотя мне так удобнее, других из моей группы я считаю это раздражающим и проблемным. С этого момента я буду обязательно использовать скобки везде.
— Ведран

13
@vedran хорошая метафора, за исключением того, что Джон Скит не сержант, он главнокомандующий :-)
— Стивло

5
@stivlo О, я уверен, что его светлость простит небольшое непослушание;) Лично я ставлю скобки после утверждений, потому что это часть каждого руководства по кодированию, которое я когда-либо видел, но я думаю, что сегодня это довольно слабый аргумент. С автоматическим форматированием кода повсюду вы никогда не должны видеть код в его первой форме, и если отступ правильный, скобки не дают никакой дополнительной информации.
— Voo

4
Еще один аргумент ВСЕГДА использовать фигурные скобки: imperialviolet.org/2014/02/22/applebug.html
— MrTJ

32

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

Иногда я не использую фигурные скобки в защитных предложениях, чтобы сделать код более компактным. Мое требование для этого состоит в ifтом, чтобы за ними следовало выражение перехода , например returnили throw. Кроме того, я держу их в одной строке, чтобы привлечь внимание к идиоме, например:

if (!isActive()) return;

Они также применимы к коду внутри циклов:

for (...) {
  if (shouldSkip()) continue;
  ...
}

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

Некоторые языки (например, Perl или Ruby) имеют своего рода условный оператор , в котором фигурные скобки не применяются:

return if (!isActive());
// or, more interestingly
return unless (isActive());

Я считаю, что это эквивалентно тому, что я только что описал, но явно поддерживаемым языком.


7
Охранные предложения +1 внутри циклов обычно более ясны без фигурных скобок.
— Viccari 04

2
Согласились на охранные статьи. На мой взгляд, делает код более читаемым и фактически увеличивает ремонтопригодность. Тем не менее, пункты, которые дает принятый ответ, очень верны, поэтому я бы ограничил пропуск фигурных скобок защитными оговорками.
— ChrisK

11

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

for (...) 
  do_something();
  do_something_else();

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

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

for (int i=0; i<3; i++);
  System.out.println("Why on earth does this print just once?");

Так что держите фигурные скобки, если у вас нет уважительной причины, это всего лишь несколько нажатий клавиш.


3
Первый пункт хорош, а второй неверен. У версии с скобками все еще может быть эта проблема. для (int я = 0; я <3; я ++); {System.out.println ("Почему это печатается только один раз?"); }. Я знаю это, потому что всегда использую фигурные скобки, но иногда по ошибке добавляю лишние точки с запятой.
— emory

3
Версия с фигурной скобкой может иметь ее, но она более заметна, если фигурная скобка находится на той же строке. Со скобкой на следующей строке это действительно так же противно.
— Mat

Вторая версия для меня так же важна, как и первая, потому что, глядя на вторую версию, почти невозможно определить, что не так, пока вы действительно не запустите ее, чтобы увидеть, что в мире происходит. Разработчики тратят много времени на отладку такого кода, который можно было бы легко заметить, если бы была введена эта изогнутая скобка. Для меня отсутствие этих волнистых скобок - это не просто вопрос стиля, а хороший индикатор вероятных ошибок в коде.
— theyCallMeJun

5

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

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

Но должен сказать, что без форматтера это может быть опасно.


В Python отступы имеют значение. В Java, C, C ++ или других языках стиля C этого не происходит.
— Кристофер Шнайдер

1
@ChristopherSchneider Это точка.
— Máté Magyar

5

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

if( "Prod".equals(stage) )
  callBankFunction ( creditCardInput )
else
  callMockBankFunction ( creditCardInput )

Теперь предположим, что у вас этот код не работает из-за какой-то внутренней проблемы. Вы хотите проверить ввод. Итак, вы вносите следующее изменение:

if( "Prod".equals(stage) )
  callBankFunction ( creditCardInput )
else
  callMockBankFunction ( creditCardInput )
  Logger.log( creditCardInput )

Скажем, вы исправили проблему и развернули этот код (и, возможно, рецензент и вы думаете, что это не вызовет проблемы, поскольку он не находится в состоянии «Prod»). Волшебным образом в ваших производственных журналах теперь печатается информация о кредитной карте клиента, которая видна всем сотрудникам, которые могут просматривать журналы. Не дай бог, если кто-то из них (со злым умыслом) завладеет этими данными.

Таким образом, отказ от фиксации и небольшое небрежное кодирование часто может привести к нарушению безопасности информации. Он также классифицируется как уязвимость в JAVA CERT - Software Engineering Institure, CMU .


Я бы сказал, что это, во-первых, довольно ужасный дизайн, но суть верна.
— Кристофер Шнайдер

4

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

Когда вы используете скобки, вы объявляете блок кода:

{

//Block of code
}

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

for( ; ; )
  if(a == b) 
    doSomething()

более читабельно написано в скобках, если нет необходимости:

for( ; ; ) {
  if(a == b) {
    doSomething()
   }
}

4

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


3

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


Я согласен с этим. Скобки не для вас. Они для человека, который идет за вами. Несколько раз у меня был код, который я утверждал, что я был незнаком, в котором не использовались скобки и были плохие отступы. На этом этапе я, вероятно, исправляю ошибку, поэтому хорошо знать, что должно произойти. Отсутствие фигурных скобок делает это менее очевидным, и мне приходится проходить код, теряя время.
— Кристофер Шнайдер

2

Больше поддержки группой "всегда подтяжки" от меня. Если вы опускаете фигурные скобки для циклов / ветвей с одним оператором, поместите оператор в ту же строку, что и оператор управления,

if (condition) doSomething();
for(int i = 0; i < arr.length; ++i) arr[i] += b;

так сложнее забыть о вставке скобок, когда тело расширено. Тем не менее, все равно используйте кудри.


2

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


1

С точки зрения результата это то же самое.

Только две вещи, которые нужно учитывать.

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

Примечание: по моим наблюдениям, если это цикл с в цикле. Внутренняя петля без подтяжек также безопасна. Результат не изменится.


1

Если у вас есть только один оператор внутри цикла, он будет таким же.

Например, см. Следующий код:

for(int i=0;i<4;i++)
            System.out.println("shiva");

у нас есть только одна инструкция в приведенном выше коде. так что нет проблем

for(int i=0;i<4;i++)
            System.out.println("shiva");
            System.out.println("End");

Здесь у нас есть два оператора, но только первый оператор входит в цикл, но не второй оператор.

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


1

Если вы удалите фигурные скобки, будет прочитана только первая строка инструкции. Никакие дополнительные строки не читаются. Если у вас есть более 1 строки инструкций для выполнения, пожалуйста, используйте фигурные скобки - иначе будет сгенерировано исключение.


1

В настоящее время очень легко изменить отступ кодов, чтобы узнать, какой блок кодов находится в каком ifили for/ while. Если вы настаиваете на том, что изменить отступы сложно, то квадратные скобки, размещенные с неправильным отступом, могут также сильно запутать вас.

for(int i = 0; i < 100; i++) { if(i < 10) {
    doSomething();
} else { for(int j = 0; j < 5; j++) {
        doSomethingElse();
    }
}}

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

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

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

for(int i = 0; i < 100; i++) {
    if(i < 10) {
    doSomething();
}
else {
    for(int j = 0; j < 5; j++) {
        doSomethingElse();
    }
}

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

ИМХО, человек, пишущий код, обязан проверить код и убедиться, что вещи имеют правильный отступ, прежде чем они приступят к другим вещам.


0

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


0

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

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.