PostgreSQL NULL против отдельной таблицы - PullRequest
0 голосов
/ 20 мая 2018

У меня есть постоянно растущая таблица с именем transactions, которая растет ~ 10 миллионов строк в месяц.

В этой таблице есть столбец jsonb с именем extra.

70%.столбца extra записей transactions имеют значение NULL, а остальные имеют значение json, например:

{
   "lang": "en",
   "pages": 3,
   "message": "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Egestas purus viverra accumsan in nisl nisi. Arcu cursus vitae congue mauris rhoncus aenean vel elit scelerisque. In egestas erat imperdiet sed euismod nisi porta lorem mollis. Morbi tristique senectus et netus. Mattis pellentesque id nibh tortor id aliquet lectus proin. Sapien faucibus et molestie ac feugiat sed lectus vestibulum..."
}

Примечание: все ключи extra json фиксированы для всех строки не изменится.

Обзор таблицы transactions:

id |  price  | type |    extra    
-------------------------------------------
 1 | 2000.00 | SMS  |     null    
 2 | 2000.00 | SMS  |     null    
 3 | 4000.00 | SMS  |     null    
 4 | 5000.00 | SMS  | {"lang": "en", "pages":8, "message":"Lore..."}
 5 | 4000.00 | SMS  |     null    
 6 | 4000.00 | SMS  |     null    
 7 | 5000.00 | SMS  | {"lang": "de", "pages":5, "message":"Some..."}

Почему я это сделал?

I 'используя столбец jsonb вместо трех отдельных столбцов, чтобы избежать множества значений NULL.

При jsonb у меня только 30% NULL только на 1 столбец, но когда я использую 3 отдельных столбца вместо 1 столбца jsonbУ меня есть 30% NULL для каждого столбца.

Вопрос:

Это хорошая идея, чтобы разделить мой столбец extra на 3 отдельных столбца?

Примерно так:

id |  price  | type | lang  | pages |  message       
--------------------------------------------
 1 | 2000.00 | SMS  |  null |  null | null
 2 | 2000.00 | SMS  |  null |  null | null
 3 | 4000.00 | SMS  |  null |  null | null
 4 | 5000.00 | SMS  |  en   |   8   | Lorem...
 5 | 4000.00 | SMS  |  null |  null | null
 6 | 4000.00 | SMS  |  null |  null | null
 7 | 5000.00 | SMS  |  de   |   5   | Some...

Или вместо этого я могу добавить дополнительную таблицу (например, transaction_info) с отношением один-к-одному.Вот так:

транскейшн

id |  price  | type
-------------------
 1 | 2000.00 | SMS 
 2 | 2000.00 | SMS 
 3 | 4000.00 | SMS 
 4 | 5000.00 | SMS 
 5 | 4000.00 | SMS 
 6 | 4000.00 | SMS 
 7 | 5000.00 | SMS 

action_info

id |  transaction_id  | lang  | pages |  message       
--------------------------------------------
 1 |       4          |   en  |   8   |  Lorem...
 2 |       7          |   de  |   5   |  Some...

При таком подходе у меня нет никакихЗначения NULL в обеих таблицах.

Какой из них вы предпочитаете?

1 Ответ

0 голосов
/ 20 мая 2018

Вы должны прочитать о нормальных формах - 1. NF говорит - каждое значение атомарно.Это предполагает, что любой атрибут имеет собственный столбец - обычно это хорошая идея (когда количество атрибутов меньше 50).Значение NULL требует только 1 бита - и, вероятно, хранение данных в чистом реляционном 1NF более эффективно, чем в формате JSON.

Итак, поскольку у вас новых столбцов всего три, мой ответ на ваш вопрос - да.Это хорошая идея.

Второй вопрос - одна или две таблицы - нет четкого ответа - оба варианта верны с точки зрения реляционной модели.Если в реальности есть видимое разделение - есть две сущности, тогда я предпочитаю две таблицы.В других местах (и когда количество столбцов невелико) я предпочитаю одну таблицу.

...