Отрицательное целочисленное переполнение в PostgreSQL - PullRequest
0 голосов
/ 28 ноября 2018

Я проводил некоторые тесты на Postgres с использованием расширения tinyint, когда наткнулся на что-то удивительное в отношении его диапазона.При наборе select -128::tinyint он дал мне сообщение ERROR: tinyint out of range, которое совсем не то, что я ожидал.

Предполагая, что отрицательные числа должны быть на 1 больше (или меньше), чем положительный максимум (127 для одногоцелые числа байтов) Я думал, что это ошибка с расширением, однако, попробовав это с нерасширенными числами, я обнаружил, что происходит то же самое.

select -32768::smallint -> вне диапазона

select -2147483648::integer -> вне диапазона

select -9223372036854775808::bigint -> вне диапазона

В отношении документации по типу числовых данных (https://www.postgresql.org/docs/current/datatype-numeric.html) все эти числа должны быть возможны -все отрицательные числа на единицу меньше -32767, -2147483647, -9223372036854775807 работают правильно, поэтому мне любопытно, почему это происходит, или это вообще происходит с копиями других людей.

Я пытался использовать оба postgresql10 и postgresql 11 на рабочем столе Ubuntu 16.x.

1 Ответ

0 голосов
/ 28 ноября 2018

I думаю это потому, что оператор приведения :: имеет более высокий приоритет, чем знак минус.

Таким образом, -32768::smallint выполняется как -1 * 32768::smallint, что действительно неверно.

Исправление в скобках: (-32768)::smallint или использование стандартного оператора SQL cast(): cast(-32768 as smallint)

...