Чт Сен 25, 2008 04:31 Замедление работы после сбора статистики
Полезность: Нет оценки
Кода проходил сертификацию, то в лекции по организации доступа прочел, что необходимо обязательно собирать статистику на схеме командой EXECUTE DBMS_STATS.GATHER_SCHEMA_STATS(‘имя владельца’,cascade=>true). На тот момент статистику на схеме собирали последний раз при внедрении пару лет назад. Я собрал статистику второй раз, но после сбора стали тормозить запросы. Я на тесте ещё раз протестировал. Удалил там статистику, потом заново собрал. Где-то сбор статистики существенно замедляет выполнение селекта (например, в представлениях по счетам-фактурам, по платежным документам), где-то наоборот, существенно ускоряет запрос (например, загрузку при открытии меню "Документ РЦ").
Например, я собрал статистику для таблицы Z#FACTURA_DOC запросом DBMS_STATS.GATHER_TABLE_STATS ('IBS','Z#FACTURA_DOC'). После этого в файле трассировки время загрузки представления VW_CRIT_FACTURA_DOC_SALE около 11000 мс. Если удалить статистику по таблице, то время загрузки около 3000 мс. Изменение параметров сбора статистики не влияет на время.
С чем может быть связано замедление работы после сбора статистики? Может, какие-то параметры базы влияют на это?
Еще бы сам запрос посмотреть, и план с собранной статистикой и без нее но что интересно - полный просмотр явно не маленькой таблички Z#document , короче нужен сам запрос + statspack -а отчет за период выполнения отчета(желательно) если сегодня кинешь посмотрю - ежели нет то через 3 недели после отпуска - . Системную статистику рекомендую собрать - в начале последнего дня месяца (условно если знаешь что будет хорошая нагрузка в интервал запуска)
execute dbms_stats.gather_system_stats('Start');
execute dbms_stats.gather_system_stats('Stop'); в конце рабочего дня (ну или нагрузочного интервала) - системная статистика поможет оптимизатору. После сбора статистики - чтобы немедленно увидеть результат - влияние стоимости процессорных затрат и устройств ввода-вывода на планы оптимизатора почисть разделяемый пул - alter system flush shared pool; ну и до кучи напиши что за железо - ну и вот собственно неплохой материальчик http://docs.nojabrsk.ru/sol10/B12037_01/server.101/b10752/optimops.htm
Последний раз редактировалось: Serj (Пт Сен 26, 2008 06:38), всего редактировалось 1 раз
SELECT
A1_1.Id ID, A1_1.CLASS_ID Class_Id, A1_1.STATE_ID State_Id,
A1_1.C_DOCUMENT_NUM C_1,
A1_1.C_DOCUMENT_DATE C_2,
decode(A1_1.C_KIND#0, 1, 'На покупку', 2, 'На продажу', 3, 'Нал. агент') C_3,
decode(A1_1.C_INITION, null, 'первичный', 'оплаченный') C_4,
A1_1.C_SUM_FACT C_5,
nvl(A5_1.C_NAME,A1_1.C_CL_DT#2#2) C_6,
nvl(A9_1.C_NAME,A1_1.C_CL_KT#2#2) C_7,
nvl(A6_1.C_MAIN_V_ID,A1_1.C_CL_DT#2#1) C_8,
nvl(A7_1.C_MAIN_V_ID,A1_1.C_CL_KT#2#1) C_9,
decode(A1_1.C_CL_KT#0, 1, A9_1.C_INN, 2, A1_1.C_CL_KT#2#INN) C_10,
A1_1.C_SERV_LIST REF11,
DECODE((select count(1) from Z#SERVICE tc where tc.collection_id=A1_1.C_SERV_LIST and rownum=1),0,'{...}','{***}') C_11,
A1_1.C_DATE_OPRIX C_12,
A1_1.C_DATE_PAY C_13,
A1_1.C_INFO_MAIN_DOCUM C_14,
A8_1.C_CUR_SHORT C_15, A1_1.C_VALUTA REF15,
A1_1.C_INITION REF16,
DECODE(A1_1.C_INITION,null,null,'(***)') C_16,
A1_1.C_CONN REF17,
DECODE((select count(1) from Z#TMC_FACT_CONN tc where tc.collection_id=A1_1.C_CONN and rownum=1),0,'{...}','{***}') C_17,
A1_1.C_NUM_FACT C_18,
z$factura_doc_lib.get_sum_fact(A1_1.ID) C_19,
z$factura_doc_lib.get_nds_sum_fact(A1_1.ID) C_20,
z$factura_doc_lib.get_nds_rate_fact(A1_1.ID) C_21,
nvl(Z$FACTURA_DOC_CONN_LIB.get_doc_num(A1_1.ID), A13_1.C_DOCUMENT_NUM) C_22,
nvl(Z$FACTURA_DOC_FACTURA_INFO_LIB.get_ref_docum(A1_1.ID), A1_1.C_DOCUMENT) REF23,
DECODE(nvl(Z$FACTURA_DOC_FACTURA_INFO_LIB.get_ref_docum(A1_1.ID), A1_1.C_DOCUMENT),null,null,'(***)') C_23,
Z$FACTURA_DOC_CONN_LIB.get_doc_sum(A1_1.ID) C_24,
A12_1.C_NAME C_25, A1_2.C_DOCUMENT_USER REF25,
A10_1.C_CODE C_26, A1_1.C_DEPART REF26,
A11_1.C_CODE C_27, A10_1.C_PART REF27,
A1_1.C_NUMB_SALE C_28,
A1_1.State_ID REF29,
A1_1_S.NAME C_29,
A1_1.C_KIND#0 U_1,
A1_1.C_DEPART U_2,
A1_1.C_FILIAL U_3
FROM Z#FACTURA_DOC A1_1,
Z#CLIENT A5_1,
Z#AC_FIN A6_1,
Z#CLIENT A9_1,
Z#AC_FIN A7_1,
Z#DEPART A10_1,
Z#DOCUMENT A13_1,
Z#USER A12_1,
Z#DOCUMENT A1_2,
Z#FT_MONEY A8_1,
Z#CL_PART A11_1, STATES A1_1_S
WHERE A1_1.C_CL_DT#1#1 = A5_1.ID(+)
AND A1_1.C_CL_DT#1#2 = A6_1.ID(+)
AND A1_1.C_CL_KT#1#1 = A9_1.ID(+)
AND A1_1.C_CL_KT#1#2 = A7_1.ID(+)
AND A1_1.C_DEPART = A10_1.ID(+)
AND A1_1.C_DOCUMENT = A13_1.ID(+)
AND A1_2.C_DOCUMENT_USER = A12_1.ID(+)
AND A1_1.ID = A1_2.ID
AND A1_1.C_VALUTA = A8_1.ID(+)
AND A10_1.C_PART = A11_1.ID(+)
AND A1_1.STATE_ID = A1_1_S.ID(+) AND A1_1.CLASS_ID = A1_1_S.CLASS_ID(+)
AND (A1_1.State_Id = 'ACTIVE'
and (A1_1.C_KIND#0=2 or A1_1.C_KIND#0=3)
)
AND
( SYS_CONTEXT('IBS_SYSTEM','ADMIN')='1' OR
SYS_CONTEXT('IBS_RIGHTS','3583')='1'
AND
( SYS_CONTEXT('IBS_RIGHTS',A1_1.CLASS_ID)='1'
)
AND (SYS_CONTEXT('IBS_ERIGHTS',A1_1.CLASS_ID||(A1_1.C_FILIAL))='0'
AND SYS_CONTEXT('IBS_ERIGHTS',A1_1.CLASS_ID||(A1_1.C_DEPART))='0'
)
)
AND SYS_CONTEXT('IBS_OPTIONS','3583') is null
AND SYS_CONTEXT('USERENV', 'CLIENT_IDENTIFIER') is null
Гмм.. почему-то оптимизатор выбирает больше фулсканов чем просмотров индексов - не хотелось бы сходу, но первое что приходит на ум optimizer_index_cost_adj - чему равен?, если в параметрах истанса его нет то вообще не трогаем но коротко его смысл если он меньше 100 то мы говорим что доступ по индексу к данным дешевше чем фулскан, поставив
его в 10 например заставим почти всегда оптимизатор выбирать индексный доступ(только не всегда это может быть оптимально). Но я предлагаю собрать системную статистику - почистить разделяемый пул - и пробовать собрать потом статистику по таблицам и индексам участвующим в запросах, более того системную статистику имеет смысл собрать даже 2 раза в моменты наивысшей нагрузки - ну типа один раз в день и потом еще раз, планы должны "выпрямится" - если этого не произойдет(в чем я сомневаюсь) то можно ооочень аккуратно "покрутить" optimizer_index_cost_adj.
З.Ы. - у себя системную статистику собрал 1 раз - все крутится нормально, вообще системную статистику в отличии от статистики схемы нужно пере собирать если кардинально сменится железо сервера.
В трассировке стоит время загрузки около 2500 мсек. Параметр optimizer_index_cost_adj имеет значение 100. Вот только не понятно, почему, когда я собрал статистику по всей схеме на рабочей базе, то скорость работы замедлилась. Хотя сейчас вроде нормально работает.
Не подскажете ещё ответ на вопрос: в операции сбора статистики есть параметр method_opt, который по умолчанию равен 'FOR ALL COLUMNS SIZE 1'. Можно поставить 'FOR ALL COLUMNS AUTO'. Я на тесте ставил такое значение, статистика дольше собиралась. Можно использовать его значение по умолчанию или лучше поставить с AUTO? И аналогично параметр cascade, который по умолчанию false.
FOR ALL COLUMNS SIZE 1 - кол-во групп(баккетов) в гистограмме - по сути сбор без использования гистограмм(распределения данных в столбце) - можно оставить в 1-цу(хотя надо тестить планы запросов) , cascade - собирает также и по всем индексам таблицы статистику.
Спасибо за помощь. На следующей неделе ещё немного поэкспериментирую со сбором статистики. Пользователям звонил, они говорят, что замедление было один день, когда я в первый раз статистику собрал. Я сам тогда заметил, что база медленно работает.
Вы не можете начинать темы Вы не можете отвечать на сообщения Вы не можете редактировать свои сообщения Вы не можете удалять свои сообщения Вы не можете голосовать в опросах
Домен cftclub.ru не связан с ЗАО "Центр Финансовых Технологий" и ни в коей мере не нарушает авторских и иных прав
Владелец может не разделять мнения Участников и не несет ответственности за их публикации
Powered by phpBB