Mnogomernoe разделяне (дял) на Oracle данни

Един от най-мощните възможности на Oracle е възможността за разделяне на данните в таблица (разделяне), което може значително да се повиши ефективността на базата данни и да се изгради една по-оптимална и красиво логически и физически структура на таблиците и индексите. В този случай, Oracle има значително ограничение. Можете да създадете само две нива на разделяне (преградни - subpartition). Понякога това не е достатъчно, и бих искал да се създаде по-добра разделяне на данни, например на 3 нива, 4 или повече.
Аз ще ви покажа един конкретен пример колко лесно е да се получи около това. Този подход позволява да създавате произволен брой вложени разделяне, ограничен само от въображението ни. осъществимост и ограничения на Oracle.

Условието на задачата.
Налице е процес на репликация на данни от множество бази данни едновременно в един, данните трябва да се съхраняват в продължение на дни от седмицата и разделени използва по-късно време. Размерът на данни в рамките на един ден може да достигне повече от 25 млрд. Strings, тъй като за по-нататъшната обработка е желателно да се отделят по време на пристигането си в таблицата. Този проблем е реален. Най-общо казано, системата трябва да поддържа търговски етаж на фондовата борса в режим 24/7. Огромният обем е следствие на електронната търговия. а именно запазването на търговските кавички (Търговски кавички) през целия ден. по този начин езика на Oracle, имаме:

TRD_DB_ID -> 1, ..., 30 - ID база данни от които има репликация. такива бази данни. в този пример 30
DAY_OF_WEEK_ID -> 1. 5 - ID делничен
TIME_SLICE_ID -> 1, ..., 48 - период ID. Всички часа са разделени в полу-часови интервали.

Основана идея е да се споделят огромни количества данни в обособени части, за да позволи повторение паралелно (TRD_DB_ID), които се използват отново в паралел и независимо изпомпване DATEWARHOUSE данни (TIME_SLICE_ID) и способността да подкрепи търговията през целия ден и през цялата седмица. Огромен удобство това разделение се крие във факта. можете да направите, да се рестартира на всеки процес помпа независимо от останалите и да изпълнява команди TRUNCATE независимо и, ако е необходимо в паралел за няколко дяла едновременно, което значително ще намали времето на изготвянето на базата данни за по-нататъшна употреба.
Има проблем. Необходимо е да се ниво 3 разделяне на данните. Oracle позволява само 2. Ако погледнете как Oracle създава таблицата на дяловете с subpartition, на физическо и логическо ниво, то е лесно да се види, че всеки SUBPARTITION не е нищо друго, като отделна единица. А основната идея на работа с този обект е. че възложителят не мисли за това как тя subpartition / дял тя работи. За да направите това, е достатъчно да се посочи в
SELECT .... ОТ ...
КЪДЕ
стойност на subpartition / преградни ключове и ORACLE автоматично ще работи само с този subpartition / дял и няма да използва пълния маса сканиране (FULL маса сканиране). Очевидно е, че на сканиране 25 млрд. Редове не са всъщност по принцип ако кажем, такава маса, използване приложение, което работи в реално време.

РЕШЕНИЕ
Ние ще използваме една и съща идея, че и Oracle. СПИСЪК ще създадете дял, където в основата на ключа ще бъде комбинираната стойност на трите независими променливи. да речем
PART_22340 - ще означава, че в дял ние ще се съхраняват данните за 2-рия ден от седмицата, от база данни # 23. за периода 40-ия ден от време (19:30 - 20:00). Очевидно е, че е необходимо да се създаде N = 30 * 5 * 48 = 7200 дялове.

Създаване на таблица SQH_AF
(C_1,
... ..
C_N,
PART_KEY INTEGER (10)
)
дял от списък (part_key)
(
дял PART_10101 стойности (10101)
дял PART_10102 стойности (10102)
дял PART_10103 стойности (01013)
... ..
преградни PART_53047values ​​(53047)
дял PART_53048 стойности (53048)
);

Тогава се създаде помощен масата
Създаване на таблица AF_REF
(
PART_KEY INTEGER (10)
DAY_OF_WEEK_ID INTEGER (1),
TRD_DB_ID INTEGER (2)
TIME_SLICE_ID INTEGER (2)
)
;
Създаване на уникални INDEX AF_REF_U1 ON AF_REF
(. DAY_OF_WEEK_ID TRD_DB_ID TIME_SLICE_ID.);
;
Коя е изпълнен в лесния начин
************************************************** ***
************************************************** ******************************
И по-нататък построен VIEW
създаване или замени оглед SQH_AF_V
като
изберете
a.C_1,
a.C_2,
...
a.C_N,
b.PART_KEY, b.DAY_OF_WEEK_ID, б. TRD_DB_ID, b.TIME_SLICE_ID

от SQH_AF а, б AF_ref
където
a.part_key = b.part_key;

Ясно е, че INSERT разумно произвеждат, знаейки предварителните стойностите на всички променливи, за да се определи PART_KEY. Но SELECT, използвайки SQH_AF_V.
По-долу е ОБЯСНЕТЕ ПЛАН за да се покаже. че Oracle ще работят с отделна секция, а не цялата маса

изберете * от SQH_AF_V
където
TRD_DB_ID = 1
и
TIME_SLICE_ID = 4
и
DAY_OF_WEEK_ID = 1;


план
SELECT ОБЯВЯВАНЕ ALL_ROWS Цена: 1 Bytes: 216 кардиналност: 4
5 вложени цикъла стойност: 1 байта 216 кардиналност: 4
2 ТАБЛИЦА НА ДОСТЪПА НА INDEX ROWID TABLE DBA_ADMIN.AF_REF Цена: 1 Bytes: 46 кардиналност: 1
1 INDEX UNIQUE SCAN INDEX (уникални) DBA_ADMIN.AF_REF_U1 стойност: 0 кардиналност: 1
4 PARTITION СПИСЪК итератор Цена: 0 Bytes: 32 кардиналност: 4 Partition #: 4 дяла, определени от ключови стойности
3 TABLE ДОСТЪП пълна маса DBA_ADMIN.SQH_AF Цена: 0 Bytes: 32 кардиналност: 4 Partition #: 4 дяла, определени от ключови стойности

Една малка добавка. Ако използвате Oracle 11g и виртуални високоговорители, може да се изгради една маса

Създаване на таблица SQH_AF
(C_1,
... ..
C_N,
TRD_DB_ID INTEGER (2)
DAY_OF_WEEK_ID INTEGER (1),
TIME_SLICE_ID INTEGER (2)
PART_KEY AS DAY_OF_WEEK_ID * 10,000 + TRD_DB_ID * 100 + TIME_SLICE_ID
)
дял от списък (part_key)
(
дял PART_10101 стойности (10101)
дял PART_10102 стойности (10102)
дял PART_10103 стойности (01013)
... ..
преградни PART_53047values ​​(53047)
дял PART_53048 стойности (53048)
);
В този случай, можете да вмъкнете колона в таблица, незабавно и Oracle автоматично ще определи разпределението.