C ++ !!преобразование в bool - PullRequest
2 голосов
/ 11 ноября 2011

В C ++ есть конструкция !!, применимая к значениям не bool, чтобы преобразовать ее в bool. Например:

int n = 12;

if ( !!n )
  std::<<cout << "n is true";
else
  std::<<cout << "n is false";

Есть ли какие-либо ограничения, где это может быть применено, или какие типы применимы: POD, указатели и т. Д .?

Ответы [ 5 ]

8 голосов
/ 11 ноября 2011

Ограничение состоит в том, что operator! должен быть определен для типа (и он должен давать тип, для которого также определено operator!)

5 голосов
/ 11 ноября 2011

Работает для любого типа, который может быть оценен в логическом контексте.Итак, арифметические типы, типы указателей (включая указатель на (член) (функцию)) и все, что угодно с преобразованием в один из них.Плюс шансы и окончания, такие как enum типы, std::nullptr_t, и, возможно, что-то еще, что я забыл.4/3 в C ++ 11 определяет, что контекстно преобразуется в bool , и это то, что делает встроенный operator!.

Для всех этих типов, написание if(!!n)избыточно, вы можете написать if(n) с тем же значением.!!n для таких типов означает то же самое, что и bool(n) или static_cast<bool>(n);.

. Это также работает для любого типа с перегруженным operator!, который возвращает тип, который может быть преобразован в bool (или который возвращаеттип с operator! перегружен для возврата bool).

Если крайний левый operator! возвращает тип, отличный от bool, тогда вы все равно сможете написать if(!!n), но !! нене действует как преобразование в bool.Он действует как преобразование в любой тип возвращаемого значения.

3 голосов
/ 11 ноября 2011

Другие ответы хороши для вашего актуального вопроса.

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

if (n!=0) 
    { 
      //whatever
    }

Явное тестирование на ноль имеет преимущество в том, что вы помните, помните ли вы соглашение «ноль - ложь», используемое в c ++. См. https://stackoverflow.com/q/329582/498253, и комментарии ниже.

Это потому, что для меня if(!!my_int) не очень понятно - неясно, что должно произойти, и формирование ветви в этой точке похоже на то, что это вызовет проблемы.

Предыдущий фрагмент (так что очень полезные комментарии имеют смысл)

bool my_bool = (n != 0) ? true : false; //whichever way you want it to work.
if (my_bool) 
  { 
    //whatever
  }
2 голосов
/ 11 ноября 2011

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

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

struct A
{
  int a;
  float b;
};

но следующий может:

struct B
{
  int v;
  operator int()
  {
    return v;
  }
};
0 голосов
/ 11 ноября 2011

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

Редактировать:

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...