Думайте, булі, а не шматочки
Підсумовуючи це, рішення вашого професора є кращим (але все-таки неправильним, строго кажучи, див. Далі), оскільки він використовує булові оператори замість розрядних операторів і трактує булеві числа як цілі числа. Вираз c==1
для позначення "c є істинним" є невірним, тому що якщо c може бути числом (згідно з заявленим призначенням), то будь-яке ненульове значення c повинно вважатися репрезентуючим true
.
Дивіться це запитання щодо того, чому краще не порівнювати булеви з 0 або 1, навіть коли це безпечно.
Однією з дуже вагомих причин не користуватися xor
є те, що це експрес- ексклюзив чи операція. Це трапляється у вашому прикладі, тому що і ліва, і права сторона є булевими виразами, які перетворюються на 1 або 0 (див. Знову 1 ).
Булева ексклюзивна або є насправді !=
.
Розбиття виразу
Щоб краще зрозуміти рішення вашого професора, найпростіше замінити булеві оператори на їх "альтернативні лексеми" еквівалентами, що перетворює його на кращу редагуваність (imho) та повністю еквівалентний код C ++: Використання "не" для "!" і ви отримаєте "і" за && "
(not a and not b) != c
На жаль, немає жодного логічного exclusive_or
оператора, окрім цього not_eq
, що не допомагає в цьому випадку.
Якщо ми розбиваємо природний вираз мови:
Або a, і b є і хибними, або c є істинними, але не обидва.
спочатку в реченні про булеві пропозиції А і В:
Або А, або В, але не обидва.
це означає A != B
(лише для булевих, а не для будь-якого типу A і B).
Тоді пропозиція А була
a і b є хибними
які можна констатувати як
a - хибна, а b - хибна
що перекладається на (not a and not b)
, і нарешті
c - це правда
Що просто перекладається на c
. Поєднуючи їх, ви отримуєте знову (not a and not b) != c
.
Для подальшого пояснення того, як працює цей вираз, я відкладаю до таблиць істинності, які інші дали у своїх відповідях.
Ви обоє помиляєтесь
І якщо я можу нітрик: Оригінальне завдання зазначало, що a, b і c можуть бути невід'ємними числами, але не однозначно зазначало, що якщо вони були числами, вони повинні бути обмежені значеннями 0 і 1. Якщо є якесь число, яке є не 0 являє собою true
, як це прийнято, тоді наступний код дасть дивовижну відповідь :
auto c = 2; // "true" in some way
auto a = 0; // "false"
auto b = 0; // "false"
std::cout << ((!a && !b) != c);
// this will output: 1 (!)
// fix by making sure that != compares booleans:
std::cout << ((!a && !b) != (bool)c);
a == b or c
замістьa == b or a ==c
. Проблема полягає в тому, що розмовна затримка є неточною і насправді обидві інтерпретації можуть бути дійсними