Что происходит, когда я вычитаю целое без знака из целого числа со знаком в C ++? - PullRequest
10 голосов
/ 16 марта 2011

Что произойдет, если я сделаю что-то вроде этого:

unsigned int u;
int s;

...
s -= u;

Каково ожидаемое поведение этого:

1) Предполагается, что целое число без знака не слишком велико, чтобы поместиться в целое число со знаком?

2) Предполагая, что целое число без знака переполнит целое число со знаком?

Спасибо.

Ответы [ 2 ]

14 голосов
/ 16 марта 2011

В общем, обратитесь к 5/9 в стандарте.

В вашем примере значение со знаком преобразуется в без знака (принимая его мод UINT_MAX +1), затем выполняется вычитание по модулю UINT_MAX + 1 для получения результата без знака.

Сохранение этого результата в виде значения со знаком в s включает стандартное интегральное преобразование - это в 4.7 / 3.Если значение находится в диапазоне signed int, то оно сохраняется, в противном случае это значение определяется реализацией.Все реализации, на которые я когда-либо смотрел, использовали арифметику по модулю, чтобы задвинуть ее в диапазон от INT_MIN до INT_MAX, хотя, как говорит Крит, вы можете получить предупреждение за это неявное выполнение.

"Трюк"Реализации, с которыми вы, вероятно, никогда не будете иметь дело, могут иметь разные правила для unsigned-> подписанного преобразования.Например, если реализация имеет представление знаковых целых чисел со знаком, то всегда невозможно выполнить преобразование, взяв модуль, поскольку нет способа представить +/- (UNIT_MAX+1)/2 в виде целого числа.

Также имеет значение 5.17 / 7, «Поведение выражения вида E1 op= E2 эквивалентно E1 = E1 op E2, за исключением того, что E1 вычисляется только один раз».Это означает, что для того, чтобы сказать, что вычитание выполняется в типе unsigned int, все, что нам нужно знать, это то, что s - u выполняется в unsigned int: для -= нет специального правила, что арифметика должна выполняться вТип LHS.

0 голосов
/ 16 марта 2011

u преобразовывается как целое число со знаком и вычитается из s.В конечном счете, кастинг не имеет никакого значения.Один набор битов вычитается из другого, и результат переходит в s.

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