Что более приемлемо - булево присваивание через if / else или логическое выражение?


11

Что будет считаться более ремонтопригодным?

if (a == b) c = true; else c = false;

или же

 c = (a == b);

Я пытался посмотреть в Code Complete, но не могу найти ответ.

Я думаю, что первое является более читабельным (вы можете буквально прочитать его вслух), что, как мне кажется, делает его более понятным. Второй, безусловно, имеет больше смысла и уменьшает код, но я не уверен, что он так удобен для разработчиков на C # (я бы ожидал увидеть эту идиому больше, например, в Python).


3
Два не эквивалентны. Вам нужно else c = falseдля первого или сделать назначение ||=во втором.

17
Я думаю, что тот факт, что вам пришлось внести два изменения в первую форму, отвечает на ваш вопрос!
Джеймс

7
Я согласен с @James. Вторая форма, хотя и не такая многословная, очень проста для понимания и не оставляет двусмысленности относительно ее значения. Там нет никаких трюков или ярлыков, просто короткая, потому что концепция проста. Тот факт, что вы закодировали первый с ошибкой, и вам пришлось редактировать его, чтобы исправить его, и он все еще не совершенен (непоследовательное использование скобок), является доказательством того, что это не так просто, как вы думаете.
Эрик Кинг,

5
Вау, действительно ли разработчики C # считают первую форму приемлемой? Это ... серьезно снижает мое доверие к ним. По моему опыту, использование первой формы сильно намекает на полное недопонимание булевых выражений.
Андрес Ф.

2
Просто, чтобы сделать вещи интересными, вот еще один вариант:c = a==b ? true : false;
FrustratedWithFormsDesigner

Ответы:


14

Второй вариант лучше.

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

Однако я не считаю c = (a == b);это примером хитрого трюка. Это прямое представление простой концепции. Как можно проще.

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

if (a == b)
{
    c = true; 
}
else 
{
    c = false;
}

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


15

Во-первых, осознайте, что ваши две формы не эквивалентны.

if (a == b) c = true;

cбудет установлено в true, если aравно b, и если нет, его значение останется таким, каким оно уже есть.

c = (a == b);

cбудет установлено значение true, если aравно b, а если нет, то будет установлено значение false.

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

if (a == b) {
  c = true;
} else c = false;

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


Абсолютно верно - я обновил свой вопрос.
Брет Уокер

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

11

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

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

Другая причина предпочесть вторую форму в том, что вы можете объявить cи назначить ее в одном выражении, т.е.

bool c = (a == b);

Изменение переменных может легко привести к ошибкам, поэтому я бы избежал этого. Использование ifоператора требует, чтобы переменная была объявлена ​​перед условием, а затем изменена.


Я читаю два утверждения в одной строке как псевдокод
Джимми Хоффа

1
+1 за " Another reason to prefer the second form is that you can declare c and assign it in a single statement"
Андрес Ф.

0

«более ремонтопригодный» может быть очень субъективным.

Я обычно предпочитаю читаемость и намерение, а не сокращение кода. Я думаю, что вы сохраняете 8 печатных символов, используя сокращенную форму.

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

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


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

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

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

1
Написание чистого логического выражения - не хитрый трюк!
Андрес Ф.

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

0

Секунда. Он имеет меньше повторений (СУХОЙ) и легче понять, что происходит, что cимеет значение равны или нет aи быть b.

ИМХО, даже лучше было бы

c = a == b

Так же, как я бы написал

  • 1 + 2 + 3 вместо ((1 + 2) + 3)
  • 5 + 3 * 7 вместо (5 + (3 * 7))

Очевидно и тривиально ненужный код не является достоинством. Это загромождено.


-4

Избиратели, пожалуйста, уточните, что не так с моим пересмотренным ответом.

Да, c = (a == b);может быть трудно читать (еще хуже, StyleCop жалуется на ненужные скобки), но мне все еще нравится простота a == b. Поэтому вот что я люблю использовать, когда оба aи bони одинаковы:

private static bool NoPeriod
{
    get
    {
        return this.MyWaveLength == this.HerWaveLength;
    }
}

И тогда вы можете сделать: this.c = this.NoPeriodвместо:

this.c = this.MyWavelength == this.HerWaveLength;

1
так ты имел ввиду return this.MyWaveLength = this.HerWaveLength;или return this.MyWaveLength == this.HerWaveLength;вместо?
Джесси С. Slicer

5
Какая!? c = (a == b);не подвержен ошибкам. Первая форма исходного вопроса гораздо более подвержена ошибкам , о чем свидетельствует сам ОП, вынужденный редактировать свой вопрос, чтобы исправлять ошибки!
Андрес Ф.

Я полагаю, в вашем предложенном решении есть ошибка = против ==
Ондра

@ Онда Морски, спасибо ... компилятор поймал бы это для меня.
Работа

6
Я не знаком с StyleCop, но если он говорит, что ненужные круглые скобки плохие, вы должны отключить его. Ненужные скобки не нужны для компилятора, но они могут быть очень, очень хороши для человеческого глаза. Если вы написали c = a == b; компилятор может понять это просто отлично, но это сложнее для человека.
Майкл Шоу
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.