похожие утверждения, дающие разные результаты - PullRequest
3 голосов
/ 29 апреля 2020

В следующем коде:

#include <iostream>
#include <assert.h>
int main()
{
    int a,b;
    cin>>a>>b;
    char c,d;
    cin>>c>>d;
    assert ((a==b,a*b==9,c==d));
    assert ( a==b && a*b==9 && c==d );
}

Если вы:

  1. вводите разные целые числа или разные символы, первый оператор assert прерывает программу. (как и должно быть).
  2. Но, если вы введете в этом коде равные целые числа (кроме 3) и одинаковые символы, первый оператор assert не прерывает программу, однако второй оператор assert делает.

Является ли первое утверждение assert слабым или есть что-то, чего я не знаю в утверждениях assert?

Ответы [ 2 ]

5 голосов
/ 29 апреля 2020

a==b,a*b==9,c==d - выражение запятой. Для встроенного оператора запятой :

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

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

Возвращает последний операнд в качестве своего возврата значение, то есть c==d. a==b и a*b==9 оцениваются, но их результаты отбрасываются. Таким образом, assert ((a==b,a*b==9,c==d)); проверяет только c==d на самом деле.

С другой стороны, assert ( a==b && a*b==9 && c==d ); проверяет все условия; которые подключены через &&, тогда все должны быть true, чтобы пройти проверку.

1 голос
/ 29 апреля 2020

1. введите разные целые числа или разные символы, первый оператор assert прерывает программу. (как и должно быть).

Значение оператора запятой в общем выражении

e1 , e2

: - вычислить подвыражение e1, затем оценить e2; значением выражения является значение e2.

Итак, значением выражения

a==b,a*b==9,c==d

является значение

c==d

При использовании этого выражение в assert(), если c==d приводит к false, независимо от значений a и b, assert() приводит к завершению программы.

2. Но если вы введете в этом коде равные целые числа (кроме 3) и одинаковые символы, первый оператор assert не отменяет программу, а второй оператор assert делает.

Логическая операция И expr1 && expr2 использует режим короткого замыкания. При логическом коротком замыкании второй операнд, expr2, оценивается, только если результат не полностью определен первым операндом, expr1. То есть expr2 не оценивается, если expr1 является логическим 0 (false).

В выражении, данном в секундах assert()

a==b && a*b==9 && c==d

у вас есть a*b==9 вместе с a==b и c==d. Таким образом, это выражение приводит к true только тогда, когда заданы входные данные от 3 до a и b и одинаковые значения символов вводятся в c и d, в противном случае это выражение приводит к false, а утверждение приводит к завершение программы.

...