Q1
Наконец, добавлено в официальную документацию с Postgres 9.4 :
Присвоение значенияпеременная PL / pgSQL записывается как:
variable { := | = } expression;
[...] Равное (=
) может использоваться вместо PL / SQL-совместимого :=
.
Q2
Есть ли какие-либо известные последствия использования =
вместо :=
?
Да ,У меня был случай с серьезными последствиями : вызов функции с именованными параметрами - что связано, но не совсем то же самое.
Строго говоря, различие в этом случаесделано в SQL коде.Но это академическое отличие от ничего не подозревающего программиста. 1
Рассмотрим функцию:
CREATE FUNCTION f_oracle(is_true boolean = TRUE) -- correct use of "="
RETURNS text AS
$func$
SELECT CASE $1
WHEN TRUE THEN 'That''s true.'
WHEN FALSE THEN 'That''s false.'
ELSE 'How should I know?'
END
$func$ LANGUAGE sql;
В сторону: обратите внимание на правильное использование =
в определении функции.Это часть синтаксиса CREATE FUNCTION
- в стиле назначения SQL . 2
Вызов функции с именованной нотацией:
SELECT * FROM f_oracle(is_true := TRUE);
Postgres идентифицирует :=
как присвоение параметров, и все в порядке. Однако :
SELECT * FROM f_oracle(is_true = TRUE);
Поскольку =
является оператором равенства SQL, Postgres интерпретирует is_true = TRUE
как выражение SQL в контексте оператора вызова и пытаетсяоценить его перед передачей результата как безымянный позиционный параметр .Ищет идентификатор is_true
во внешней области видимости.Если это не может быть найдено:
ERROR: column "is_true" does not exist
Это счастливый случай, и, к счастью, также общий.
Когда is_true
может находится во внешней области видимости (и типы данных совместимы), is_true = TRUE
является допустимым выражением с результатом boolean
, который принимается функцией.Ошибка не возникает.Понятно, что это намерение программиста использовать SQL оператор равенства =
...
Этот SQL Fiddle демонстрирует эффект.
Очень трудно отлаживать, если вы не знаете о различии между =
и :=
.
Всегда используйте правильный оператор.
1 При использовании именованных обозначений в вызовах функций только :=
является правильным оператором присваивания.Это относится к функциям всех языков, не только PL / pgSQL, вплоть до pg 9.4.См. Ниже.
2 Можно использовать =
(или DEFAULT
) для определения значений по умолчанию для параметров функции.Это никак не связано с проблемой.Это просто замечательно близко к неправильному варианту использования.
Postgres 9.0 - 9.4: переход с :=
на =>
Стандарт SQL для присвоения именованных параметров функции: =>
(и Oracle PL / SQL использует его . Postgres не может сделать то же самое, так как оператор ранее не был зарезервирован, поэтому вместо этого он использует оператор присваивания PL / pgSQL :=
. С выпуском Postgres 9.0 используется =>
для других целей не рекомендуется. По примечаниям к выпуску :
Не рекомендуется использовать => в качестве имени оператора (Роберт Хаас)
Будущие версии PostgreSQL будутвозможно, полностью отклонить это имя оператора, чтобы поддерживать стандартную запись SQL для параметров именованных функций. На данный момент это все еще разрешено, но при определении такого оператора выдается предупреждение.
Если вы должны использовать =>
для чего-то другого, прекратите и воздержитесь. Это сломается в будущем.
Postgres 9.5: используйте =>
сейчас
Начиная с этого релизаНапример, используется стандартный оператор SQL =>
.:=
все еще поддерживается для обратной совместимости.Но используйте стандартный оператор в новом коде, который не нужно запускать на очень старых версиях.
Это относится к присвоению именованных параметров в вызовах функций (область действия SQL), а не к оператору присваивания :=
в коде plpgsql, который остается неизменным.