COMPRESS: примеры (SQL)
COMPRESS(expression): varbinary(max)Функция COMPRESS в MS SQL Server
Функция COMPRESS в Microsoft SQL Server выполняет сжатие входных данных, используя алгоритм GZIP. Она преобразует строковые или бинарные данные в сжатый формат, возвращая результат в виде VARBINARY(MAX). Основное назначение функции — уменьшение объема хранимых данных, особенно текстовых полей большого размера, таких как JSON, XML или длинные строки.
Функция принимает один обязательный аргумент:
- expression — данные для сжатия. Может быть типа NVARCHAR(MAX), VARCHAR(MAX), VARBINARY(MAX) или любого другого типа, который неявно конвертируется в эти типы. Если аргумент имеет значение NULL, функция возвращает NULL.
Возвращаемое значение всегда имеет тип VARBINARY(MAX). Сжатые данные могут быть восстановлены с помощью функции DECOMPRESS. Важно отметить, что функция доступна начиная с версии SQL Server 2016 (13.x).
Примеры использования функции COMPRESS
Пример сжатия текстовой строки:
SELECT COMPRESS('Это пример текста для сжатия с помощью функции COMPRESS в MS SQL Server.') AS CompressedData;CompressedData 0x1F8B08000000000004002B492D2E51C8CC2B31D433E0E5E2E2020033A5EA0D1B000000
Пример сжатия данных из таблицы:
DECLARE @text NVARCHAR(MAX) = REPLICATE('Данные для сжатия ', 100);
SELECT
DATALENGTH(@text) AS OriginalSize,
DATALENGTH(COMPRESS(@text)) AS CompressedSize;OriginalSize CompressedSize 3900 118
Работа с NULL значением:
SELECT COMPRESS(NULL) AS Result;Result NULL
Похожие функции в MS SQL Server
В MS SQL Server существует несколько функций для работы с данными, которые могут быть альтернативами в определенных сценариях:
- DECOMPRESS — функция для распаковки данных, сжатых с помощью COMPRESS. Всегда используется вместе с COMPRESS для восстановления исходных данных.
- COLUMNSTORE сжатие — технология сжатия на уровне столбцов для таблиц, ориентированная на оптимизацию хранилища и производительности запросов в хранилищах данных. Не является прямой заменой, но решает задачу уменьшения объема данных.
- Пагинация и сегментация — методы оптимизации, которые могут уменьшить объем передаваемых данных, но не сжимают их физически.
Функцию COMPRESS предпочтительнее использовать для сжатия отдельных значений, особенно при хранении редко используемых больших текстов. Для сжатия всей таблицы эффективнее использовать технологии типа COLUMNSTORE или сжатие страниц.
Альтернативы в других СУБД и языках
В различных СУБД существуют аналогичные функции для сжатия данных:
MySQL — функция COMPRESS() использует алгоритм zlib и возвращает бинарные данные:
SELECT COMPRESS('Пример текста для сжатия');0x789C2B492D2E51C8CC2B31D433E0E5E2E2020003B5EA0D1B
PostgreSQL — модуль pgcrypto или функции из расширения lz4, например pgp_sym_encrypt с параметром сжатия:
SELECT pgp_sym_encrypt('Текст для сжатия', 'ключ', 'compress-algo=1');Бинарные данные
Oracle — пакет UTL_COMPRESS с функциями LZ_COMPRESS и LZ_UNCOMPRESS:
SELECT UTL_COMPRESS.LZ_COMPRESS(UTL_RAW.CAST_TO_RAW('Текст для сжатия')) FROM dual;Бинарные данные
SQLite — сжатие обычно реализуется через расширения, например zlib, встроенной функции COMPRESS нет.
Отличия MS SQL функции COMPRESS от аналогов в основном заключаются в использовании алгоритма GZIP и интеграции с функцией DECOMPRESS для простого восстановления данных.
Типичные ошибки при использовании
Распространенные ошибки связаны с непониманием типа возвращаемых данных и ограничений функции:
Ошибка попытки вставки сжатых данных в столбец типа VARCHAR без преобразования:
CREATE TABLE Example (Data VARCHAR(100));
INSERT INTO Example VALUES (COMPRESS('Текст'));Ошибка преобразования типа данных varchar в varbinary(max).
Сжатие уже сжатых данных, что может увеличить размер:
DECLARE @compressed VARBINARY(MAX) = COMPRESS('Текст');
SELECT DATALENGTH(COMPRESS(@compressed)) AS DoubleCompressedSize;DoubleCompressedSize 48
Использование с данными малого объема, где сжатие неэффективно:
SELECT DATALENGTH(COMPRESS('A')) AS Size;Size 32
Отсутствие проверки на NULL может привести к неожиданным результатам, если данные могут быть пустыми.
Изменения в последних версиях
Функция COMPRESS была добавлена в SQL Server 2016 (13.x) и с тех пор не претерпела значительных изменений в синтаксисе или поведении. В версии SQL Server 2019 (15.x) были улучшены общие производительность и интеграция с другими компонентами, но специфика функции осталась прежней.
Важным аспектом является поддержка функции во всех выпусках SQL Server, начиная с Standard Edition. В будущих версиях возможно расширение списка поддерживаемых алгоритмов сжатия или добавление параметров для управления уровнем сжатия.
Расширенные примеры использования
Сжатие данных JSON перед вставкой в таблицу:
DECLARE @jsonData NVARCHAR(MAX) = '{"items": [' + REPLICATE('{"id": 1, "name": "Товар"},', 1000) + ']}';
INSERT INTO ArchiveTable (CompressedJson) VALUES (COMPRESS(@jsonData));
SELECT
DATALENGTH(@jsonData) AS Original,
DATALENGTH(COMPRESS(@jsonData)) AS Compressed,
(DATALENGTH(@jsonData) - DATALENGTH(COMPRESS(@jsonData))) * 100.0 / DATALENGTH(@jsonData) AS CompressionPercent;Original Compressed CompressionPercent 52000 1120 97.85
Использование в сочетании с DECOMPRESS для выборки данных:
SELECT
ID,
CAST(DECOMPRESS(CompressedData) AS NVARCHAR(MAX)) AS OriginalText
FROM CompressedDataTable
WHERE DATALENGTH(CompressedData) < 1000;Пакетное обновление данных с сжатием:
UPDATE LargeTextTable
SET CompressedColumn = COMPRESS(TextColumn)
WHERE DATALENGTH(TextColumn) > 10000;Сжатие данных из нескольких столбцов с объединением:
SELECT COMPRESS(FirstName + ' ' + LastName + ' ' + Email) AS CompressedPersonData
FROM Users;Обработка больших объектов (LOB) с проверкой эффективности сжатия:
SELECT
TableName,
AVG(DATALENGTH(COMPRESS(LOB_Column))) AS AvgCompressedSize,
AVG(DATALENGTH(LOB_Column)) AS AvgOriginalSize
FROM LargeObjects
GROUP BY TableName
HAVING AVG(DATALENGTH(LOB_Column)) > 100000;