Я рекомендую вам сделать это именно так, как вы показали, так как это самый прямой. Инициализируйте значение -1
, которое будет работать всегда , независимо от фактического представления знака, в то время как ~
иногда будет иметь удивительное поведение, поскольку вам потребуется правильный тип операнда. Только тогда вы получите самое высокое значение типа unsigned
.
В качестве примера возможного сюрприза рассмотрим следующий:
unsigned long a = ~0u;
Не обязательно хранить шаблон со всеми битами 1 в a
. Но сначала он создаст шаблон со всеми битами 1 в unsigned int
, а затем назначит его a
. Что происходит, когда unsigned long
имеет больше битов, так это то, что не все из них равны 1.
И рассмотрим этот, который потерпит неудачу при представлении дополнения к не-двум:
unsigned int a = ~0; // Should have done ~0u !
Причина в том, что ~0
должен инвертировать все биты. Инвертирование, которое даст -1
на машине дополнения до двух (что является необходимым значением!), Но не даст -1
в другом представлении. На машине дополнения это дает ноль. Таким образом, на машине дополнения, вышеприведенное будет инициализировать a
в ноль.
Вы должны понять, что все дело в ценностях, а не в битах. Переменная инициализируется значением . Если в инициализаторе вы измените биты переменной, используемой для инициализации, значение будет сгенерировано в соответствии с этими битами. Значение, которое вам нужно для инициализации a
до максимально возможного значения, равно -1
или UINT_MAX
. Второй будет зависеть от типа a
- вам нужно будет использовать ULONG_MAX
для unsigned long
. Однако первое не будет зависеть от его типа, и это хороший способ получить самое высокое значение.
Мы не говорим о том, имеет ли -1
все биты один (не всегда). И мы не говорим о том, имеет ли ~0
все биты один (он, конечно, имеет).
Но мы говорим о том, каков результат инициализированной переменной flags
. И для этого только -1
будет работать с каждым типом и машиной.