Mysql
 sql >> база данни >  >> RDS >> Mysql

mysql:използвайте SET или много колони?

Изглежда, че сте загрижени главно за представянето.

Няколко души предложиха разделяне на 3 таблици (таблица с категории плюс или проста таблица с кръстосани препратки или по-сложен начин за моделиране на йерархията на дървото, като вложен набор или материализиран път), което е първото нещо, което си помислих, когато прочетох въпроса ви .

С индексите, напълно нормализиран подход като този (който добавя две JOIN) все още ще има "доста добра" производителност на четене. Един проблем е, че INSERT или UPDATE към събитие сега може също да включва едно или повече INSERT/UPDATE/DELETE към таблицата с кръстосани препратки, което в MyISAM означава, че таблицата с кръстосани препратки е заключена, а в InnoDB означава, че редовете са заключени, така че ако вашата база данни е заета със значителен брой записвания, ще имате по-големи проблеми с конкуренцията, отколкото ако само редовете за събития бяха заключени.

Лично аз бих изпробвал този напълно нормализиран подход преди оптимизиране. Но предполагам, че знаете какво правите, че вашите предположения са правилни (категориите никога не се променят) и имате модел на използване (много записи), който изисква по-малко нормализирана, плоска структура. Това е напълно добре и е част от това, за което NoSQL е.

SET срещу "много колони"

И така, що се отнася до действителния ви въпрос „SET срещу много колони“, мога да кажа, че съм работил с две компании с интелигентни инженери (чиито продукти са CRM уеб приложения... едното всъщност беше управление на събития) и двете използва подхода "много колони" за този вид данни от статичен набор.

Моят съвет би бил да помислите за всички заявки, които ще правите в тази таблица (претеглени според честотата им) и как ще работят индексите.

Първо, с подхода "много колони" ще ви трябват индекси за всяка от тези колони, за да можете да правите SELECT FROM events WHERE CategoryX = TRUE . С индексите това е супер бърза заявка.

В сравнение с SET, трябва да използвате побитово И (&), LIKE или FIND_IN_SET(), за да направите тази заявка. Това означава, че заявката не може да използва индекс и трябва да извърши линейно търсене на всички редове (можете да използвате EXPLAIN, за да проверите това). Бавна заявка!

Това е основната причина SET да е лоша идея - неговият индекс е полезен само ако избирате по точни групи от категории. SET работи чудесно, ако избирате категории по събитие, но не и обратното.

Основният проблем с по-малко нормализирания подход "много колони" (в сравнение с напълно нормализирания) е, че той не се мащабира. Ако имате 5 категории и те никога не се променят, добре, но ако имате 500 и ги сменяте, това е голям проблем. Във вашия сценарий с около 30, които никога не се променят, основният проблем е, че има индекс за всяка колона, така че ако правите чести записи, тези заявки стават по-бавни поради броя на индексите, които трябва да се актуализират. Ако изберете този подход, може да искате да проверите дневника на бавните заявки на MySQL, за да се уверите, че няма извънредни бавни заявки поради спорове в натоварено време на деня.

Във вашия случай, ако вашето е типично уеб приложение с тежко четене, мисля, че да използвате подхода „много колони“ (както направиха двата CRM продукта по същата причина) вероятно е разумно. Това е определено по-бързо от SET за тази заявка SELECT.

TL;DR Не използвайте SET, защото заявката „избере събития по категория“ ще бъде бавна.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. вмъкнете няколко реда, като използвате една стойност на forigenk във формата

  2. MySQL GROUP &COUNT Няколко таблици

  3. Ограничете броя на редовете, към които да се присъедините, в mysql

  4. Store_result и get_result за изявление

  5. JSON_ARRAY_INSERT() – Вмъкване на стойности в JSON масив в MySQL