Тип даних uuid
буде відмінно підходять для виконання цього завдання. Він займає лише 16 байт на відміну від 37 байт в оперативній пам'яті для varchar
або text
представлення. (Або 33 байти на диску, але непарне число зажадає в багатьох випадках прокладки для ефективного використання 40 байт.) І uuid
тип має ще деякі переваги.
Приклад:
SELECT md5('Store hash for long string, maybe for index?')::uuid AS md5_hash
Деталі та додаткові пояснення:
Ви можете розглянути інші (дешевші) функції хешування, якщо вам не потрібен криптографічний компонент md5, але я б пішов з md5 для вашого випадку використання (здебільшого лише для читання).
Слово попередження : для вашого випадку ( immutable once written
) функціонально залежний (псевдо-природний) ПК є нормальним. Але те саме було б болем, коли text
можливі оновлення . Подумайте, щоб виправити помилку помилки: PK та всі залежні індекси, стовпці FK у dozens of other tables
інших та інших посиланнях повинні були також змінитися. Таблиця і покажчик індексу, проблеми з блокуванням, повільні оновлення, втрачені посилання, ...
Якщо text
можна змінитись у звичайній роботі, кращим вибором буде сурогатний ПК . Я пропоную bigserial
стовпцю (діапазон -9223372036854775808 to +9223372036854775807
- це дев'ять квінтільйонів двісті двадцять три квадрильйони триста сімдесят два трильйони тридцять шість щось мільярд ) різних значень billions of rows
. У будь-якому випадку це може бути хорошою ідеєю : 8 замість 16 байт для десятків стовпців та індексів FK!). Або випадковий UUID для значно більших кардинальностей або розподілених систем. Ви завжди можете зберігати вказаний md5 (as uuid
) додатково, щоб швидко знаходити рядки в головній таблиці з оригінального тексту. Пов'язані:
Щодо вашого запиту :
Щоб звернутися до коментаря @ Daniel : Якщо ви віддаєте перевагу представництву без дефісів, видаліть дефіси для відображення:
SELECT replace('90b7525e-84f6-4850-c2ef-b407fae3f271', '-', '')
Але я б не переймався. Представлення за замовчуванням просто чудово. І проблема насправді не в представництві.
Якщо інші сторони повинні мати інший підхід і кидати струни без дефісів в суміш, це теж не проблема. Postgres приймає кілька розумних подань тексту як вхідні дані для uuid
. Документація :
PostgreSQL також приймає такі альтернативні форми для введення: використання малих цифр, стандартний формат, оточений дужками, опущення деяких або всіх дефісів, додавання дефісу після будь-якої групи з чотирьох цифр. Приклади:
A0EEBC99-9C0B-4EF8-BB6D-6BB9BD380A11
{a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a11}
a0eebc999c0b4ef8bb6d6bb9bd380a11
a0ee-bc99-9c0b-4ef8-bb6d-6bb9-bd38-0a11
{a0eebc99-9c0b4ef8-bb6d6bb9-bd380a11}
Більше того, md5()
функція повертається text
, яку ви б використовували decode()
для перетворення bytea
та представлення за замовчуванням цього :
SELECT decode(md5('Store hash for long string, maybe for index?'), 'hex')
\220\267R^\204\366HP\302\357\264\007\372\343\362q
Вам доведеться encode()
знову отримати оригінальне подання тексту:
SELECT encode(my_md5_as_bytea, 'hex');
На додаток до цього, значення, що зберігаються як bytea
би займають 20 байт в оперативній пам’яті (і 17 байт на диску, 24 з прокладкою ) через внутрішні varlena
накладні витрати , що особливо несприятливо для розміру та продуктивності простих індексів.
Тут все працює на користь uuid
.