Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Oracle Новый топик    Ответить
 Помогите понять план  [new]
Corner
Member

Откуда:
Сообщений: 1270
Добрый день!

Есть два запроса, которые отличаются одним условием. Помогите понять разницу в планах

1. Запрос
          SELECT i.nssinst_id
            FROM bs.bstechsubs ts, bs.bsservinst i, bs.bsservsubs ss
           WHERE ts.ntech = :b4
             AND i.ntechsubs = ts.ntechsubs_id
             AND ss.nssubs_id = i.nssubs
План
------------------------------------------------------------------------------------------------------------------------------
| Id  | Operation                          | Name                    | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
------------------------------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT                   |                         |    13 |   390 |    23   (0)| 00:00:01 |       |       |
|   1 |  TABLE ACCESS BY GLOBAL INDEX ROWID| BSSERVINST              |     4 |    72 |     5   (0)| 00:00:01 | ROWID | ROWID |
|   2 |   NESTED LOOPS                     |                         |    13 |   390 |    23   (0)| 00:00:01 |       |       |
|   3 |    TABLE ACCESS BY INDEX ROWID     | BSTECHSUBS              |     4 |    48 |     6   (0)| 00:00:01 |       |       |
|*  4 |     INDEX RANGE SCAN               | BSTECHSUBS_TECHSUBS_IND |     4 |       |     3   (0)| 00:00:01 |       |       |
|*  5 |    INDEX RANGE SCAN                | BSSERVINST_TECHSUBS_FK  |     4 |       |     2   (0)| 00:00:01 |       |       |


2.Запрос
          SELECT i.nssinst_id
            FROM bs.bstechsubs ts, bs.bsservinst i, bs.bsservsubs ss
           WHERE ts.ntech = :b4
             AND i.ntechsubs = ts.ntechsubs_id
             AND ss.nssubs_id = i.nssubs
             AND NVL (:b3, ss.nservt) = ss.nservt

План
Plan hash value: 2476662982

----------------------------------------------------------------------------------------------------------------------------------
| Id  | Operation                              | Name                    | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
----------------------------------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT                       |                         |    14 |   588 |   101   (0)| 00:00:01 |       |       |
|   1 |  CONCATENATION                         |                         |       |       |            |          |       |       |
|*  2 |   FILTER                               |                         |       |       |            |          |       |       |
|   3 |    NESTED LOOPS                        |                         |    13 |   546 |    49   (0)| 00:00:01 |       |       |
|   4 |     NESTED LOOPS                       |                         |    13 |   390 |    23   (0)| 00:00:01 |       |       |
|   5 |      TABLE ACCESS BY INDEX ROWID       | BSTECHSUBS              |     4 |    48 |     6   (0)| 00:00:01 |       |       |
|*  6 |       INDEX RANGE SCAN                 | BSTECHSUBS_TECHSUBS_IND |     4 |       |     3   (0)| 00:00:01 |       |       |
|   7 |      TABLE ACCESS BY GLOBAL INDEX ROWID| BSSERVINST              |     4 |    72 |     5   (0)| 00:00:01 | ROWID | ROWID |
|*  8 |       INDEX RANGE SCAN                 | BSSERVINST_TECHSUBS_FK  |     4 |       |     2   (0)| 00:00:01 |       |       |
|*  9 |     TABLE ACCESS BY INDEX ROWID        | BSSERVSUBS              |     1 |    12 |     2   (0)| 00:00:01 |       |       |
|* 10 |      INDEX UNIQUE SCAN                 | PK_BSSERVSUBS           |     1 |       |     1   (0)| 00:00:01 |       |       |
|* 11 |   FILTER                               |                         |       |       |            |          |       |       |
|  12 |    NESTED LOOPS                        |                         |     1 |    42 |    52   (0)| 00:00:01 |       |       |
|  13 |     NESTED LOOPS                       |                         |    13 |   390 |    26   (0)| 00:00:01 |       |       |
|  14 |      TABLE ACCESS BY INDEX ROWID       | BSTECHSUBS              |     4 |    48 |     6   (0)| 00:00:01 |       |       |
|* 15 |       INDEX RANGE SCAN                 | BSTECHSUBS_TECHSUBS_IND |     4 |       |     3   (0)| 00:00:01 |       |       |
|  16 |      TABLE ACCESS BY GLOBAL INDEX ROWID| BSSERVINST              |     4 |    72 |     5   (0)| 00:00:01 | ROWID | ROWID |
|* 17 |       INDEX RANGE SCAN                 | BSSERVINST_TECHSUBS_FK  |     4 |       |     2   (0)| 00:00:01 |       |       |
|* 18 |     TABLE ACCESS BY INDEX ROWID        | BSSERVSUBS              |     1 |    12 |     2   (0)| 00:00:01 |       |       |
|* 19 |      INDEX UNIQUE SCAN                 | PK_BSSERVSUBS           |     1 |       |     1   (0)| 00:00:01 |       |       |
----------------------------------------------------------------------------------------------------------------------------------

Заранее спасибо.
19 авг 09, 12:02    [7555522]     Ответить | Цитировать Сообщить модератору
 Re: Помогите понять план  [new]
Andrey.L
Member

Откуда: Харьков
Сообщений: 1546
Corner,

Перепиши добавочное условие так:
AND (:b3 IS NULL OR :b3 = ss.nservt)
19 авг 09, 12:16    [7555606]     Ответить | Цитировать Сообщить модератору
 Re: Помогите понять план  [new]
Jannny
Member

Откуда: Спб
Сообщений: 6424
Вы смотрите предикаты плана, понятнее будет.
Оракл преобразовал запрос к виду :b3 = ss.nservt or ss.nservt = ss.nservt и разбил его на две части, так как ss.nservt - это PK. И чем ходить полным перебором по таблице, Оракл посчитал дешевле два раза сходить по индексу. Хотя в принципе, учитывая not null, условие ss.nservt = ss.nservt Оракл мог бы и вовсе отбросить, но это наверное слишком... :)
В первом запросе к таблце bsservsubs Оракл вообще не обращается, ему достаточно индекса по ss.nssubs_id.
ЗЫ: Вы бы приводили описание затрагиваемых в плане индексов, чтобы не приходилось догадываться...
19 авг 09, 12:16    [7555607]     Ответить | Цитировать Сообщить модератору
 Re: Помогите понять план  [new]
Corner
Member

Откуда:
Сообщений: 1270
Спасибо за помощь.
19 авг 09, 12:41    [7555747]     Ответить | Цитировать Сообщить модератору
Все форумы / Oracle Ответить