|
Программирование >> Полное сканирование таблицы
FROM USER IND COLUMNS WHERE TABLE NAME = иРРЕК(Ш) ORDER BY INDEX NAME. COLUMN POSITION: В утилите SQL*Plus, войдя в схему, содержащую таблицу, которую вы хотите проверить, запустите в строке с приглашением SQL> команду Pindex <Имя тдблицы>. В ответе утилиты будут по порядку перечислены многостолбцовые индексы, начиная с первого столбца. Далее показан пример использования сценария: SQL> @index Locations INDEX NAME COLUMNJAME LOCATION PKEY LOCATION ID SQL> Чтобы увидеть функциональные индексы и то, к чему они будут применяться (обычно это блоки запроса, где есть условия для иРРЕМ<Столбец>) или LOWER (<Сголбец>) или производится преобразование типа столбца), используйте сценарий f i ndex. sql: -- File called findex.sql set long 40 set pagesize 999 SELECT INDEX NAME. COLUMNJXPRESSION FROM USER IND EXPRESSIONS WHERE TABLE NAME = UPPERC&&r) ORDER BY INDEX NAME. COLUMN POSITION: Интерпретация плана выполнения я объяснил, как узнать порядок соединения таблиц в запросе, методы их соединения и методы доступа к ним для получения надежного плана выполнения, показанного ранее. Если вы объедините эти знания с основами, изложенными в главе 2, то сможете понять, как Oracle обращается к данным. Чтобы проверить ваше понимание, попробуйте изложить полный план вьшолнения по-русски, как набор инструкций для базы данных. Сравните ваши результаты со следующим описанием. Если возникло слишком много разногласий, попробуйте еще раз провести анализ плана выполнения после того, как прочитаете еще несколько описаний других планов, чтобы проверить, насколько улучшилось ваше понимание. Далее план выполнения описан в повествовательной форме, как инструкции для базы данных. 1. Используя условие Е. Last Name = : 1, перейти к 1шдексу EMPLOYEE LAST NAME и найти список идентификаторов строк, соответствующих сотрудникам с указанной фамилией. 2. Для каждого из этих идентификаторов строк перейти к таблице Employees (Е) и, используя ту часть идентификатора, где хранится адрес блока, считать один блок (обычно логическое считывание, если необходимо - физическое) для каждого идентификатора строки из предыдущего шага. Используя часть идентификатора, содержащую адрес строки, найти эту запись, на которую указывает ее идентификатор, и считать из нее все необходимые данные (запрошенные для псевдонима Е). 3. Для каждой такой строки, используя условие соединения Е. Manager ID=M. Empl oyee ID, перейти к индексу по первичному ключу EMPLOYEE PKEY и найти один подходя- щий идентификатор строки, соответствующий записи сотрудника для менеджера того работника, чью запись вы уже считали ранее. Если соответствия не найдено, отбросить результирующую строку, которая строится в данный момент. 4. Если же подходящая запись найдена, следует перейти к таблице Employees (М) и, используя ту часть идентификатора строки, где хранится адрес блока, считать один блок (логическое считывание, если требуется - физическое), соответствующий идентификатору строки из предыдущего шага. Используя ту часть идентификатора строки, где хранится адрес записи, найти ту строку, на которую указывает этот идентификатор, и считать из нее все необходимые данные (запрошенные для псевдонима М). Присоединить подходящие данные к строке, полученной при предыдущем считывании из таблицы, чтобы создать частичную результирующую строку. 5. Для каждой такой строки, используя условие соединения М. Locat i оп 1 D=LM. Loca -tion ID, перейти к индексу по первичному ключу LOCATION PKEY и найти единственный подходящий идентификатор строки, указывающий на запись о местоположении, соответствующую менеджеру сотрудника, запись которого вы уже считали. Если соответствия не найдено, отбросить результирующую строку, которая строится в данный момент. 6. Если искомое соответствие все же найдено, для подходящего идентификатора строки перейти к таблице Locations (LM) и, используя ту часть идентификатора строки, где хранится адрес блока, считать один блок (логическое считывание, если требуется - физическое), соответствующий идентификатору строки из предыдущего шага. Используя ту часть идентификатора строки, где хранится ее адрес, найти определенную строку, на которую указывает данный идентификатор, и считать из нее все необходимые данные (запрошенные для псевдонима LM). Присоединить подходящие данные к строке, полученной при предьщущих считываниях из таблиц, чтобы создать частичную результирующую строку. 7. Для каждой подобной строки, используя условие соединения Е. Locati on ID=LE. Locati on ID, перейти к индексу по первичному ключу LO(TION PKEY и найти единственный подходящий идентификатор строки, обозначающий запись о местоположении для сотрудника, чью запись вы уже считали. Если соответствия не найдено, отбросить результирующую строку, которая строится в данный момент. 8. В ином случае для подходящего идентификатора строки перейти к таблице Locati ons (LE) и, используя ту часть идентификатора строки, где хранится адрес блока, считать один блок (логическое считывание, если необходимо - физическое), соответствующий идентификатору строки из предыдущего шага. Используя ту часть идентификатора строки, где хранится адрес строки, найти определенную строку, на которую указывает идентификатор строки, и считать из нее все необходимые данные (запрошенные для псевдонима LE). Присоединить подходящие данные к строке, полученной при предыдущих считываниях из таблиц, чтобы завершить результирующую строку. Отбросить всю результирующую строку, если она содержит данные, не удовлетворяющие условию L)PPER( LE. Descri pti on)=: 2. Иначе немедленно возвратить полностью построенную результирующую строку. ПРИМЕЧАНИЕ в плане выполнения вы не навдете явного шага для последнего фильтра, который отбрасывает строки, не удовлетворяющие условию для описания местоположения. Я называю этот фильтр фильтром *пос-лесчитывания , так как он не является частью метода обращения к строке таблицы, а лишь используется для удаления некоторых строк уже после того, как те были считаны. Oracle не выполняет удаление по подобным фильтрам явно в плане выполнения, но вы всегда можете рассчитывать, что Oracle сделает это при первой же возможности, как только получит данные, необходимые для оценки истинности условий фильтров. Если в плане выполнения есть еще соединения после этого последнего соединения, Oracle будет выполнять их только для строк, которые прошли фильтр посмсчитьюания, отбрасывая остальные. Ненадежные планы выполнения Настраиваемые вами планы для SQL-запросов зачастую сначала будут ненадежными, внося свой вклад в проблему недостаточной производительности, которую вам следует решить. В таких ненадежных планах выполнения используются методы соединения, отличные от вложенных циклов. От вас не требуется глубокого понимания тех планов вьшолнения, которые нельзя считать оптимальными, нужно только суметь увидеть, что это не те планы, которые вы хотите получить. Однако полезно иметь хотя бы общее представление о том, почему эти планы вьшолнения такие медленные, и знать, насколько лучше будут ваши оптимальные планы. Теперь я покажу, как выглядят альтернативные планы вьшолнения для запроса, с которым мы работали в последних двух разделах. Если я удалю все индексы, синтаксический оптимизатор создаст новый план выполнения: PLAN SELECT STATEMENT MERGE JOIN SORT JOIN MERGE JOIN SORT JOIN MERGE JOIN SORT JOIN TABLE ACCESS FULL 4*EMPL0YEES SORT JOIN TABLE ACCESS FULL 3*EMPL0YEES SORT JOIN TABLE ACCESS FULL 2*L0CATI0NS SORT JOIN TABLE ACCESS FULL 1*L0CATI0NS Порядок соединения в этом плане такой же, но теперь база данных производит соединения методом сортировки слиянием, и ищет строки в каждой таблице путем полного ее сканирования. Соединения хэшированием более распространены в критичных к ресурсам планах выполнения, чем соединения слиянием, и иногда вы даже будете предпочитать их соединениям методом вложенных циклов, поэтому далее я привожу пример с соединением подобного типа. Обратите внимание, что в исходном SQL-запросе, для которого был создан предыдущий план, сразу же за ключевым словом SELECT есть выражение /*+ RULE */. Если я заменю выражение /*+ RULE */ выражением / *+ORDERED USE HASH(M LE LM) */ и изменю порядок в разделе FROM, то с пустыми таб-
|
© 2006 - 2024 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки. |