sql >> Databáze >  >> RDS >> Mysql

Proč je délka řádku AVG 4krát větší, než se očekávalo?

Existuje mnoho důvodů, proč je průměrná velikost řádku vysoká.

  • Je to přiblížení. (Zjistil jsem, že je typicky 2x-3x vysoký.) V jednom extrémním případě -- jeden řádek v tabulce -- bude vyžadovat 16384 bajtů na řádek. To je jeden blok InnoDB. Počet řádků v tabulce je odhadovaný . Místo na disku použité pro řádky je přesné, ale viz režie níže. Průměrná velikost řádku je podíl těchto dvou.

  • Režie na sloupec -- 1 nebo 2 bajty

  • Režie na řádek – 20–30 bajtů – pro zpracování transakcí, hledání řádků v bloku atd

  • Režie na blok -- určitý počet bajtů na blok 16 kB

  • Režie pro thrashing v BTree -- min je asi 1/16 bloku, maximum je asi polovina bloku, průměr je asi 30 % po spoustě smazání a/nebo náhodných vložení.

  • Režie pro předběžné přidělení částí diskového prostoru (1 MB? 8 MB?)

  • Jak se tabulka rozrůstá z toho, že se vejde do jednoho bloku, algoritmus rozvržení se posune a procento režie dočasně naroste.

  • Smazané řádky nevracejí svůj prostor operačnímu systému, takže velikost souboru zůstává konstantní, čímž se zvyšuje zdánlivý velikost řádku.

  • Pokud nemáte explicitní PRIMARY KEY nebo UNIQUE klíč, který lze povýšit na PK, pak pro PK existuje nepřístupné 6bajtové pole (na řádek).

  • Velký TEXT /BLOB a dokonce VARCHAR jsou uloženy „mimo záznam“. To značně komplikuje výpočty. A to závisí na tom, který ze 4 ROW_FORMATs používáte. V některých případech je pro každou takovou buňku 20bajtový "ukazatel".

  • FOREIGN KEY omezení nepřidávají k požadovanému prostoru, kromě toho, že mohou vynutit vytvoření indexu.

  • INDEXes , jiný než PRIMARY KEY nejsou součástí avg_row_length.

  • PRIMARY KEY obvykle zahrnuje velmi malou režii v datech BTree. Jednoduché pravidlo palce je 1 % režie (na vrcholu samotného sloupce). Tato režie představuje nelistové uzly BTree.

  • Zatímco je transakce InnoDB zaneprázdněna, všechny upravené řádky jsou uchovávány v "seznamu historie". To vede k větší režii.

  • (Ne úplně souvisí). COMPRESSED od InnoDB má problémy -- poskytuje pouze asi 2x kompresi, na rozdíl od typické komprese textu 3x. Stojí to trochu RAM, protože je potřeba mít současně komprimovaná i nekomprimovaná data v buffer_pool (alespoň pro některé bloky).

SHOW TABLE STATUS a načítání z information_schema.TABLES dává stejná data. Existují způsoby, jak nějaké získat vhled do hloubky B+stromu pro data a pro každou tabulku.




  1. Poslední index daného podřetězce v MySQL

  2. Kolekce PL/SQL:Vnořená tabulka v databázi Oracle

  3. Kód chyby:1452. Nelze přidat nebo aktualizovat podřízený řádek

  4. mysql vyberte nejnižší cenu z více výběrů