Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Oracle Новый топик    Ответить
Топик располагается на нескольких страницах: [1] 2 3   вперед  Ctrl      все
 Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Freehover
Member

Откуда: г. Ровно, Украина
Сообщений: 23
Здравствуйте!
В PL/SQL-процедуре есть конструкция вида:
for C in (select bla-bla
            from bla-bla
           where X = X
             and (a = 1 or 
                 a != 1 
                 and ДОП_АНАЛИЗ)
          ) loop ...;
ДОП_АНАЛИЗ увеличивает время работы процедуры в сотню раз.
В большинстве случаев а=1 и ДОП_АНАЛИЗ не нужен, но выполняется всегда.
В какую сторону смотреть чтобы не выполнялся ДОП_АНАЛИЗ при а=1?
3 ноя 10, 12:32    [9724370]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
bdsm_sql
Member

Откуда:
Сообщений: 948
/*+ ORDERED PREDICATES */
3 ноя 10, 12:37    [9724420]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
брадобрей
Member

Откуда:
Сообщений: 4696
ORDERED_PREDICATES
3 ноя 10, 12:44    [9724488]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
bdsm_sql
Member

Откуда:
Сообщений: 948
ага, пардон, попутал
3 ноя 10, 12:44    [9724494]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Сергей Арсеньев
Member

Откуда:
Сообщений: 4118
Freehover,

А, чисто случайно, "Доп. анализ" не связан с запросами к другим табличкам в зависимости от значений полей таблицы bla-bla?

Просто оптимизатору может казаться, что развернуть это все в hash-join а потом уж отсечь эффективнее nested loops. :)
3 ноя 10, 12:47    [9724527]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
collow
Member

Откуда:
Сообщений: 324
Если там всё равно идёт фуллскан, то можно условие свернуть в case
3 ноя 10, 12:49    [9724544]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Freehover
Member

Откуда: г. Ровно, Украина
Сообщений: 23
Сергей Арсеньев
А, чисто случайно, "Доп. анализ" не связан с запросами к другим табличкам в зависимости от значений полей таблицы bla-bla?

create or replace procedure PROC(sProcParam  in varchar2,
                                 sProcParam1 in varchar2,
                                 sProcParam2 in varchar2,
                                 sProcParam3 in varchar2
                                 --...
                                 ) as
  sA varchar2(100);
  --...
begin
  sA := rtrim(sProcParam1) || rtrim(sProcParam2) || rtrim(sProcParam3) || '1';
  for C in (select TA.AFIELD, TA.AFIELD1, TA.AFIELD2 --...
              from TABLE_A TA
             where ((sProcParam is null and TA.AFIELD is not null) or
                   TA.AFIELD in (select TB.BFLD
                                   from TABLE_B TB
                                  where TB.BFLD1 like sProcParam
                                 --or ... разбор sProcParam
                                 ))
               and (sA = '1' or 
                   sA != '1'
                   --ДОП_АНАЛИЗ:
                   -- sProcParam1
                   and (sProcParam1 is null or
                   TA.AFIELD1 in (select TC.CFLD1
                                         from TABLE_C TC
                                        where TC.CFLD2 like sProcParam1
                                       --or ... разбор sProcParam1
                                       ))
                   -- sProcParam2
                   and (rtrim(sProcParam2) is null or
                   TA.AFIELD2 in (select TC.CFLD1
                                         from TABLE_C TC
                                        where TC.CFLD2 like sProcParam2
                                       --or ... разбор sProcParam2
                                       )))) loop
    null; --...
  end loop;
end;
т.е. связан опосредованно, опять же через OR
3 ноя 10, 13:40    [9725024]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Freehover
Member

Откуда: г. Ровно, Украина
Сообщений: 23
bdsm_sql
/*+ ORDERED PREDICATES */

/*+ ORDERED PREDICATES */ не помогло
Да, забыл - БД Oracle 9.
3 ноя 10, 13:41    [9725040]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
bdsm_sql
Member

Откуда:
Сообщений: 948
вместо пробела в хинте подчеркивание
3 ноя 10, 13:41    [9725044]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Freehover
Member

Откуда: г. Ровно, Украина
Сообщений: 23
bdsm_sql
вместо пробела в хинте подчеркивание

ну да,
...
for C in (select /*+ ORDERED_PREDICATES */ TA.AFIELD, TA.AFIELD1, TA.AFIELD2 --...

- не повлияло :(
3 ноя 10, 13:46    [9725083]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
andrey_anonymous
Member

Откуда: Москва
Сообщений: 18388
Freehover
Сергей Арсеньев
А, чисто случайно, "Доп. анализ" не связан с запросами к другим табличкам в зависимости от значений полей таблицы bla-bla?

create or replace procedure PROC(sProcParam  in varchar2,
                                 sProcParam1 in varchar2,
                                 sProcParam2 in varchar2,
                                 sProcParam3 in varchar2
                                 --...
                                 ) as
  sA varchar2(100);
  --...
begin
...
             where ((sProcParam is null and TA.AFIELD is not null) or
                   TA.AFIELD in (select TB.BFLD...
                                 ))
               and (sA = '1' or 
                   sA != '1'
                   --ДОП_АНАЛИЗ:
                   -- sProcParam1
                   and (sProcParam1 is null or
                   TA.AFIELD1 in (select TC.CFLD1...
                                       ))
                   -- sProcParam2
                   and (rtrim(sProcParam2) is null or
                   TA.AFIELD2 in (select TC.CFLD1...
...
т.е. связан опосредованно, опять же через OR


Поскольку sA - параметр, сравниваемый с литералом, попробуйте ему сказать /*+ use_concat */.
Если немного повезет - получите в плане несколько веток, каждая из которых будет прикрыта фильтром по sA, что позволяет oracle динамически исключать ненужные ветки из плана.
3 ноя 10, 13:49    [9725116]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Сергей Арсеньев
Member

Откуда:
Сообщений: 4118
Freehover,

А создать два курсора и выбирать по какому из них бегать не проще чем городить костыли для СВО?
3 ноя 10, 13:51    [9725135]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
Freehover
Member

Откуда: г. Ровно, Украина
Сообщений: 23
Сергей Арсеньев
А создать два курсора и выбирать по какому из них бегать не проще чем городить костыли для СВО?

Как последний вариант, искал что-нибудь красивее :)
Спасибо всем ответившим!
3 ноя 10, 13:57    [9725190]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
AlexFF__|
Member

Откуда:
Сообщений: 2855
Freehover
...В большинстве случаев а=1 и ДОП_АНАЛИЗ не нужен, но выполняется всегда...

Очень сомнительно
3 ноя 10, 14:23    [9725407]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
alex-ls
Member

Откуда: Иркутская обл - Пенза - Москва
Сообщений: 6916
DECODE/CASE обрабатывают условия по порядку
3 ноя 10, 14:31    [9725465]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
JaRo
Member

Откуда:
Сообщений: 1659
Вы бы:
1) рассказали, как смотрите, что выполняется всегда
2) приложили бы план запроса с предикатами
3 ноя 10, 19:20    [9727381]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
ПЕНСИОНЕРКА
Member

Откуда: Владимирская обл
Сообщений: 4728
Freehover,


автор
ДОП_АНАЛИЗ увеличивает время работы процедуры в сотню раз.
В большинстве случаев а=1 и ДОП_АНАЛИЗ не нужен, но выполняется всегда.
В какую сторону смотреть чтобы не выполнялся ДОП_АНАЛИЗ при а=1?



for C in (select bla-bla
            from bla-bla
           where X = X
             and (a = 1 or 
                   (a != 1  and ДОП_АНАЛИЗ)   //почему на строке нет скобок
                   ) loop ...;

3 ноя 10, 19:28    [9727407]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
JaRo
Member

Откуда:
Сообщений: 1659
ПЕНСИОНЕРКА
почему на строке нет скобок
Потому что они не нужны.
3 ноя 10, 19:29    [9727412]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
ПЕНСИОНЕРКА
Member

Откуда: Владимирская обл
Сообщений: 4728
JaRo
ПЕНСИОНЕРКА
почему на строке нет скобок
Потому что они не нужны.


а здесь тоже не нужны?

where 
     id=1
or (id=2 and client=3)
or (id=3 and data_kon >now)
3 ноя 10, 19:35    [9727435]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
ПЕНСИОНЕРКА
Member

Откуда: Владимирская обл
Сообщений: 4728
никогда не надо предугадывать приоритет операций

вероятность ошибки очень велика

несколько скобок не стоят нескольких часов разбирательства
3 ноя 10, 19:39    [9727450]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
JaRo
Member

Откуда:
Сообщений: 1659
ПЕНСИОНЕРКА
JaRo
ПЕНСИОНЕРКА
почему на строке нет скобок
Потому что они не нужны.
а здесь тоже не нужны?
where 
     id=1
or (id=2 and client=3)
or (id=3 and data_kon >now)
Да уж. И что мешает проверить? Или Вам лишь бы что-то сказать?..

ПЕНСИОНЕРКА
никогда не надо предугадывать приоритет операций
Нда... Не пробовали доку читать? не придется угадывать...

ЗЫ: В печальное зрелище превратился форум всего-то за один год...
3 ноя 10, 19:45    [9727484]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
xtender
Member

Откуда: Мск
Сообщений: 5704
JaRo
Нда... Не пробовали доку читать? не придется угадывать...

Вообще говоря даже не доку, а обычные учебники для программеров 1 курса...
Но в целом у нее мысль правильная - оформлен код должен быть так, чтобы читалось одним взглядом, не бегая по простыне глазами в поисках возможных ошибок

JaRo
ЗЫ: В печальное зрелище превратился форум всего-то за один год...

терпеть не могу таких заявлений. особенно, от зарегистрированного "26 февраля 2010, 10:40"
3 ноя 10, 21:09    [9727835]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
xtender
Member

Откуда: Мск
Сообщений: 5704
Freehover

(a = 1 or
 a != 1 and
 ДОП_АНАЛИЗ)

К чему такая мантра? Достаточно
(a = 1 or ДОП_АНАЛИЗ)
3 ноя 10, 21:23    [9727909]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
suPPLer
Member

Откуда: Харків, Україна
Сообщений: 7794
Блог
xtender
JaRo
ЗЫ: В печальное зрелище превратился форум всего-то за один год...

терпеть не могу таких заявлений. особенно, от зарегистрированного "26 февраля 2010, 10:40"


Не судите, да не судимы будете. ;) Или, по крайней мере, не ограничивайтесь датой её регистрации, а почитайте сообщения.

xtender
Вообще говоря даже не доку, а обычные учебники для программеров 1 курса...


Вообще-то говоря, лучше конкретную документацию. Потому что приоритеты, они разные в языках бывают.
3 ноя 10, 21:25    [9727918]     Ответить | Цитировать Сообщить модератору
 Re: Как обойти вычисление всех ветвей OR, если 1-я = TRUE?  [new]
xtender
Member

Откуда: Мск
Сообщений: 5704
suPPLer

Не судите, да не судимы будете. ;) Или, по крайней мере, не ограничивайтесь датой её регистрации, а почитайте сообщения.

Да я как раз про "не судите", не люблю, когда так судят, мол, пришли тут какие-то и испортили...

suPPLer
Вообще-то говоря, лучше конкретную документацию. Потому что приоритеты, они разные в языках бывают.

Не знаю ни одного языка, где приоритет and отличался бы от or. Максимальную разницу, которую знаю - это различие приоритетов OR и || в perl'e, но это совсем другое дело
3 ноя 10, 21:38    [9727967]     Ответить | Цитировать Сообщить модератору
Топик располагается на нескольких страницах: [1] 2 3   вперед  Ctrl      все
Все форумы / Oracle Ответить