Шаг 125 - БД Oracle - Оценка табличных пространств - дефрагментация

Настало, наконец, время заняться серьезными вещами! :) Любая операция ввода-вывода, о которой мы говорили ранее, как следствие влечет за собой фрагментацию табличного пространства. Еще ее можно назвать фрагментацией экстентов (extent fragmentation). Возникает она при изменении размещения экстентов в табличном пространстве. Может происходить либо за счет фрагментации свободного пространства, либо за счет фрагментации таблиц. Как правило следует избегать размещения в одном разделе таблиц с разными уровнями активности. Экстент можно назвать свободным (free extents), если он никогда не выделялся для сегментов табличного пространства, либо был освобожден в результате удаления сегментов. Фрагментации экстентов бывают разных типов. Например, если изолированные наборы свободных экстентов, распределены по всему табличному пространству, то такая фрагментация называется - фрагментация типа "швейцарский сыр" (Swiss cheese fragmentation) или пузырьковой фрагментацией (bubbling). При наличии смежных свободных экстентов, которые распределены по всему свободному табличному пространству - фрагментация называется - "сотовой фрагментацией" (honeycomb fragmentation). Каждый из этих двух типов фрагментации является - "фрагментацией со свободными экстентами" (free space fragmentation). Существует так же и - "фрагментация таблиц" (table fragmentation), то есть динамическое расширение таблицы за пределы ее исходных экстентов. Из всего вышесказанного ясно, что чрезмерная фрагментация приводит к замедлению вашей БД. Так как для поисков разрозненных участков, например таблицы при проведении запроса к ней может потребовать существенно большего времени, в отличие от таблицы расположенной одним "не равным" экстентом! Надеюсь это понятно!

Давайте углубимся в это еще немного! В жизни это вам пригодится! Итак, создается табличное пространство. В нем создается сегмент имеющий, скажем, один экстент состоящий из n-блоков Oracle! Ясно? Вот так весь этот механизм строится. Сегмент так же может состоять из нескольких разделов - экстентов. Еще раз повторюсь сами по себе экстенты представляют собой группы смежных блоков Oracle. Когда уже существующий экстент уже не может вместить в себя данные - сегмент получает еще один экстент. Вот так! Процесс продолжается до тех пор пока в файле данных не останется больше места, либо пока не будет достигнуто внутреннее максимальное количество экстентов на сегмент! Уловили? Для упрощения управления сегментами лучше, чтобы каждый сегмент данных содержал по одному экстенту! Вот по этому параметр хранения сегмента - initial определяющий размер начального экстента должен быть достаточно большим, чтобы обработать все данные сегмента! Кстати, если сегмент состоит из нескольких экстентов, то это не дает гарантии, что они расположены рядом друг с другом. Для примера можно сказать, что выполнить операцию DROP TABLE для таблицы содержащей, скажем, 3000 экстентов при хорошем стечении обстоятельств может занять 5-10 мин. А вот попробуйте удалить дефрагментированную таблицу в 60 000 экстентов, для этого Вам понадобится целый день! Давайте посмотрим, как себя чувствует наша учебная табличка CUSTOMERS? Дадим вот такой запрос:

SELECT TABLESPACE_NAME,
		OWNER,
		SEGMENT_NAME,
		SEGMENT_TYPE,
		EXTENTS,
		BLOCKS,
		BYTES
FROM DBA_SEGMENTS
WHERE TABLESPACE_NAME = 'USERS' AND
SEGMENT_NAME = 'CUSTOMERS' 
AND OWNER = 'MILLER'
/

Получаем:

SQL> SELECT TABLESPACE_NAME,
  2  		OWNER,
  3  		SEGMENT_NAME,
  4  		SEGMENT_TYPE,
  5  		EXTENTS,
  6  		BLOCKS,
  7  		BYTES
  8  FROM DBA_SEGMENTS
  9  WHERE TABLESPACE_NAME = 'USERS' AND
 10  SEGMENT_NAME = 'CUSTOMERS'
 11  AND OWNER = 'MILLER'
 12  /

TABLESPACE_NAME OWNER   SEGMENT_NAME  SEGMENT_TYPE EXTENTS    BLOCKS    BYTES
--------------- ------- ------------- ------------ ---------- ---------- ----------
USERS           MILLER  CUSTOMERS     TABLE        2          16         131072

Да! результат не веселый! Хотя бы тот факт, что табличка уже размазалась по двум экстентам! Да размерчик у нее что-то больно велик. Так вот для того, чтобы уменьшить "расходы" при работе с сильно фрагментированными таблицами в Oracle 8i и старше введены локально управляемые табличные пространства! (locally managed tablespaces), в которых информация об использовании экстентов хранится в битовой карте в заголовке файла данных, а не в словаре данных. Вот так и решили проблему. А, теперь давайте посмотрим информацию об экстентах одного сегмента данных. Все той же нашей таблички CUSTOMERS. Дадим вот такой запрос:

SELECT TABLESPACE_NAME,
		OWNER,
		SEGMENT_NAME,
		SEGMENT_TYPE,
		EXTENT_ID,
		BLOCK_ID,
		BYTES
		BLOCKS
FROM DBA_EXTENTS
WHERE TABLESPACE_NAME = 'USERS'
AND SEGMENT_NAME = 'CUSTOMERS'
AND OWNER = 'MILLER'
/

Получаем:

SQL> SELECT TABLESPACE_NAME,
  2  		OWNER,
  3  		SEGMENT_NAME,
  4  		SEGMENT_TYPE,
  5  		EXTENT_ID,
  6  		BLOCK_ID,
  7  		BYTES
  8  		BLOCKS
  9  FROM DBA_EXTENTS
 10  WHERE TABLESPACE_NAME = 'USERS'
 11  AND SEGMENT_NAME = 'CUSTOMERS'
 12  AND OWNER = 'MILLER'
 13  /

TABLESPACE_NAME OWNER  SEGMENT_NAME SEGMENT_TYPE  EXTENT_ID BLOCK_ID  BLOCKS
--------------- ------ ------------ ------------- --------- --------- -------
USERS           MILLER CUSTOMERS    TABLE         0         41        65536
USERS           MILLER CUSTOMERS    TABLE         1         49        65536

В вашем случае информация может и отличаться, но мой сервер по такому запросу дает именно это! Как можно видеть таблица находится в двух экстентах. Само собой напрашивается вопрос "как же все-таки решать проблему дефрагментации табличных пространств"? А, вот с этим мы далее и разберемся! А, пока усваивайте выше изложенное.


Предыдущий Шаг | Следующий Шаг | Оглавление
Автор Летучий Сергей.