citext. Тип данных для строк, нечувствительных к регистру
В исходном дистрибутиве установлено по умолчанию: нет.
Связанные компоненты: отсутствуют.
Схема размещения:
ext.
Модуль предоставляет тип данных citext для строк, нечувствительных к регистру. Сравнивая значения, он вызывает внутри себя функцию lower(). В остальном почти не отличается от типа text.
Стандартный способ с использованием функции lower() при сравнении значений имеет ряд недостатков:
- необходимо всегда обрабатывать функцией
lowerстолбец и значение; - для использования индекса необходимо создать функциональный индекс с функцией
lower; - при работе со столбцами типа
UNIQUEилиPRIMARY KEYнеявно создаваемый индекс будет чувствительным к регистру. Соответственно он не сможет использоваться при регистронезависимом поиске, а также не будет обеспечивать уникальность вне учета регистра.
Применение типа данных citext позволяет исключить вызовы функции lower() в SQL-запросах и позволяет сделать первичный ключ регистронезависимым.
Типы text и citext учитывают локаль. Это означает, что сравнение символов в верхнем и нижнем регистре зависит от правил LC_CTYPE для базы данных. Такое поведение идентично использованию функции lower() в запросах, и поскольку оно реализуется прозрачно типам данных, в самих запросах ничего дополнительно делать не нужно.
Доработка
Доработка не проводилась.
Ограничения
Существуют следующие ограничения:
- Смена регистра символов в
citextзависит от параметраLC_CTYPEбазы данных. Принцип, используемый при сравнении значений, определяется на этапе ее создания. Здесь важно учитывать, что сравнение не будет действительно регистронезависимым. Так, если установленное правило сортировки предназначено для одного языка, а в БД имеются данные на разных языках, то пользователи могут получать неожиданные результаты запросов. - Операторы
citextпринимают во внимание явное указаниеCOLLATE, сравнивая строки в нижнем регистре, но изначальное приведение в нижний регистр всегда выполняется согласно параметруLC_CTYPEбазы данных, как если бы указывалосьCOLLATE "default"; - Тип
citextне так эффективен, какtext, поскольку функции операторов и функции сравнения для B-дерева должны делать копии данных и переводить их в нижний регистр для сравнения. Кроме того, с типомtextвозможно исключение дубликатов в B-дереве. Тем не менее, регистронезависимое сравнение с использованиемcitextприменяется эффективней, чем с применениемlower. - Тип
citextмалополезен в ситуациях, когда требуется сравнивать данные без учета регистра в одних контекстах, и с учетом регистра — в других. Когда регистронезависимое сравнение требуется относительно редко, скорее используютtextи вручную вызывают функциюlower. В случаях, когда чаще требуется регистронезависимое сравнение, имеет смысл сохранить данные в столбце типаcitextи приводить их к типуtextдля регитрозависимого сравнения. Для того, чтобы в обоих случаях поиск был быстрым, потребуются два индекса. - Содержащая операторы
citextсхема должна находиться в текущем путиsearch_path(обычно это схемаpublic), в противном случае будут вызываться регистрозависимые операторы для типаtext. - Рекомендуется учитывать преобразование регистра (
case mapping) и выравнивание регистра (case folding). Например, в случаях, когда одной букве в верхнем регистре соответствуют две буквы в нижнем регистре, вместоcitextиспользуются недетерминированные правила сортировки.
Установка
При наличии прав администратора СУБД включение модуля возможно выполнить вручную:
CREATE EXTENSION citext SCHEMA ext;
Настройка
Настройка не требуется.
Использование модуля
Пример использования:
CREATE TABLE users (
nick CITEXT PRIMARY KEY,
pass TEXT NOT NULL
);
INSERT INTO users VALUES ( 'larry', sha256(random()::text::bytea) );
INSERT INTO users VALUES ( 'Tom', sha256(random()::text::bytea) );
INSERT INTO users VALUES ( 'Damian', sha256(random()::text::bytea) );
INSERT INTO users VALUES ( 'NEAL', sha256(random()::text::bytea) );
INSERT INTO users VALUES ( 'Bjørn', sha256(random()::text::bytea) );
Выборка данных по условию:
SELECT * FROM users WHERE nick = 'Larry';
Оператор SELECT вернет один кортеж, несмотря на то, что в столбец nick записано значение larry, а в запросе фигурирует Larry:
nick | pass
-------+--------------------------------------------------------------------
larry | \x303a9ace5a8c75b2f528794477d183d0f59a4969e1fca8e332254ed3cea15ad9
(1 row)
Ссылки на документацию разработчика
Дополнительно поставляемый модуль citext.