Периодически мне интересно об этом:
ИЛИ короткого замыкания всегда будет возвращать то же значение, что и оператор без короткого замыкания ИЛИ?
Я ожидаю, что короткое замыкание ИЛИ всегда будет оцениваться быстрее. Итак, был ли введен оператор без короткого замыкания ИЛИ в язык C # для согласованности?
Что я пропустил?
f()
возбуждает исключение, рассмотримtrue || f()
иtrue | f()
. Вы видите разницу? Первое выражение оценивает какtrue
, а второе вычисляет исключение.Ответы:
Оба операнда предназначались для разных вещей, происходящих из C, который не имеет логического типа. Версия с коротким замыканием || работает только с логическими значениями, а версия без короткого замыкания | работает с целочисленными типами, выполняя побитовое или. Просто так получилось, что это логическая операция без короткого замыкания для логических значений, которые представлены одним битом, равным 0 или 1.
http://en.wikibooks.org/wiki/C_Sharp_Programming/Operators#Logical
источник
|
оператор при применении к двум логическим значениям компилируется в тот жеor
оператор в CIL, как и при применении к двум целочисленным значениям - в отличие от того,||
который компилируется в CIL с использованиемbrtrue
для условного Прыгать.|
(побитовое или) должно быть без короткого замыкания для таких типов, какint
. Это потому, что почти во всех случаях вам нужно вычислить обе стороны|
выражения, чтобы вычислить правильный результат. Например, что является результатом7 | f(x)
?Если
f(x)
не оценивается, вы не можете сказать.Кроме того, было бы непоследовательным вызывать короткое замыкание этого оператора
bool
, если оно не является коротким замыканиемint
. Между прочим, я думаю, что я никогда не использовал|
намеренно логические сравнения, находя это очень неудобным, чтобы говорить|
как логический оператор.||
однако для логических сравнений, где оценка короткого замыкания работает нормально.То же самое справедливо даже для C и C ++, где происхождение этих операторов.
источник
Это правильно, оператор ИЛИ короткого замыкания (||) всегда будет возвращать то же значение, что и оператор ИЛИ без короткого замыкания (|). (*)
Однако, если первый операнд является истинным, оператор короткого замыкания не будет вызывать оценку второго операнда, в то время как оператор без короткого замыкания всегда будет вызывать оценку обоих операндов. Это может повлиять на производительность, а иногда и на побочные эффекты.
Таким образом, есть смысл использовать и то и другое: если вы заботитесь о производительности, а оценка второго операнда не приводит к каким-либо побочным эффектам (или если вы не заботитесь о них), то непременно используйте оператор короткого замыкания. , Но если по какой-то причине вам нужны побочные эффекты второго операнда, вам следует использовать оператор без короткого замыкания.
Пример, где вы должны использовать оператор без короткого замыкания:
(*) За исключением некоторого действительно извращенного сценария, где оценка первого операнда ложными причинами побочным эффектом приводит к тому, что второй операнд оценивается как истинный вместо ложного.
источник
Было бы две причины использовать вариант без короткого замыкания:
сохранение побочных эффектов (но это проще для кода с временной переменной)
предотвратить атаки по времени , избегая разветвления в коротком замыкании (это может даже повысить эффективность времени выполнения, если второй операнд является переменной, но это микрооптимизация, которую компилятор может сделать в любом случае)
источник
если правое предложение оператора имеет побочный эффект, и программист предполагал, что он хочет, чтобы оба побочных эффекта произошли до проверки их возвращаемого значения.
источник