пейнлемдюжхх х опюбхкю унпньецн рнмю дкъ пюгпюанрвхйю SQL

Author: Tina London
Date: August 7, 1992
оЕПЕБНД: нЯХОНБ д.л.

1.0 бБЕДЕМХЕ

мЮГМЮВЕМХЕЛ ЩРНЦН ДНЙСЛЕМРЮ ЪБКЕРЯЪ НОПЕДЕКЕМХЕ РПЕАНБЮМХИ Х ОПЮБХК ПЮГПЮАНРЙХ SQL ОПНЦПЮЛЛ Б МЮЬЕЛ ОНДПЮГДЕКЕМХХ, ЯНАКЧДЕМХЕ ЙНРНПШУ ОНГБНКХР ЯНГДЮБЮРЭ ЙЮВЕЯРБЕММШЕ ОПХКНФЕМХЪ. ю РЮЙФЕ НАПЮРХРЭ БМХЛЮМХЕ МЮ ЯРХКЭ МЮОХЯЮМХЪ ОПНЦПЮЛЛ, ОНЯЙНКЭЙС ОПЮБХКЭМШИ ЯРХКЭ НАКЕЦВЮЕР ОПНЖЕЯЯ ОНДДЕПФЙХ ОПНЦПЮЛЛ.

пЮГПЮАНРВХЙЮЛ ЯКЕДСЕР ОПХМХЛЮРЭ БН БМХЛЮМХЕ, ВРН Б ЪГШЙЮУ ВЕРБЕПРНЦН ОНЙНКЕМХЪ (ЙЮЙ Х Б ЪГШЙЮУ РПЕРЭЕЦН ОНЙНКЕМХЪ) ОЕПБШИ Х НВЕБХДМШИ БЮПХЮМР ОПНЦПЮЛЛШ МЕ НАЪГЮРЕКЭМН ЪБКЪЕРЯЪ КСВЬХЛ.

нЯНАНЕ БМХЛЮМХЕ МЮДН НАПЮРХРЭ МЮ МЕНАУНДХЛНЯРЭ ОПХДЕПФХБЮРЭЯЪ НОПЕДЕКЕММНЦН ЯРХКЪ ОПХ МЮОХЯЮМХХ SQL НОЕПЮРНПНБ, ОНЛХЛН БЯЕЦН ОПНВЕЦН ЩРН ОНГБНКХР ОПНЦПЮЛЛЮЛ БНЯОНКЭГНБЮРЭЯЪ ОПЕХЛСЫЕЯРБНЛ SQL ЙЩЬЮ Б Oracle V7. яЕДЭЛЮЪ БЕПЯХЪ Oracle ХЛЕЕР МЕЙХИ SQL ЙЩЬ, Б ЙНРНПНЛ ЯНДЕПФЮРЯЪ ПЮГНАПЮММШЕ (parsed) SQL ГЮОПНЯШ. Oracle НОПЕДЕКЪЕР МЮУНДХРЯЪ КХ ГЮОПНЯ Б ЙЩЬЕ Я ОНЛНЫЭЧ МЕ ВСБЯРБХРЕКЭМНЦН Й ПЕЦХЯРПС ЯПЮБМЕМХЪ.

яКЕДСЕР ХЛЕРЭ ББХДС, ВРН БНГЛНФЕР ОПНЯЛНРП ЙНДЮ, ЙНРНПШИ ХЯОНКЭГСЕРЯЪ ДКЪ ДНЯРСОЮ Й ад МЮ ЯЕПБЕПЕ Я ОНЛНЫЭЧ SQLtrace, Я ОНЯКЕДСЧЫЕИ НАПЮАНРЙНИ БШБНДЮ ОПНЦПЮЛЛНИ tkprof.

2.0 яРХКЭ МЮОХЯЮМХЪ SQL НОЕПЮРНПНБ

2.1 нЯМНБМШЕ ОНКНФЕМХЪ

SQL НОЕПЮРНПШ ЯКЕДСЕР ОХЯЮРЭ РЮЙХЛ НАПЮГНЛ, ВРНАШ НАКЕЦВХРЭ ОПНЖЕЯЯ ХУ ВРЕМХЪ, ОНМХЛЮМХЪ Х ХЯОПЮБКЕМХЪ. кНЦХВЕЯЙХ НАНЯНАКЕММЮЪ ОНЯКЕДНБЮРЕКЭМНЯРЭ НОЕПЮРНПНБ ДНКФМЮ МЮУНДХРЭЯЪ Б НРДЕКЭМНЛ ТЮИКЕ.

  1. нОЕПЮРНПШ ЯКЕДСЕР БШПЮБМХБЮРЭ РЮЙ, ВРНАШ РЕЙЯР ОПНЦПЮЛЛШ НМХ БШЦКЪДЕК ЮЙЙСПЮРМН.
  2. йЮФДНЕ ХГ ГЮОПЮЬХБЮЕЛШУ Б SELECT ОНКЕИ ДНКФМН АШРЭ МЮ НРДЕКЭМНИ ЯРПНЙЕ.
  3. йЮФДЮЪ ХГ РЮАКХЖ, ОЕПЕВХЯКЕММШУ Б FROM ДНКФМЮ АШРЭ МЮ НРДЕКЭМНИ ЯРПНЙЕ.

2.2 йКЧВЕБШЕ ЯКНБЮ SQL

  1. йКЧВЕБШЕ ЯКНБЮ Oracle ЯКЕДСЕР ОХЯЮРЭ опнохямшлх асйбюлх
  2. оЕПЕВХЯКЕММШЕ МХФЕ ЙКЧВЕБШЕ ЯКНБЮ ЯКЕДСЕР ОХЯЮРЭ Я МНБНИ ЯРПНЙХ:
              SELECT
              INTO
              FROM
              WHERE
              AND/OR
              GROUP BY
              HAVING
              CONNECT BY
              FOR UPDATE OF
              ORDER BY
  3. бЯЕ ЙКЧВЕБШЕ ЯКНБЮ Б ОПЕДЕКЮУ НДМНЦН SQL НОЕПЮРНПЮ ЯКЕДСЕР ОХЯЮРЭ Я НДМНИ Х РНИ ФЕ ОНГХЖХХ. оПХ ХЯОНКЭГНБЮМХХ БКНФЕММШУ НОЕПЮРНПНБ SELECT ХУ ЯКЕДСЕР ЯДБХЦЮРЭ БМСРПЭ ОПЕДКНФЕМХЪ МЮ ОНГХЖХЧ БРНПНЦН ЯКНБЮ Б ОПЕДШДСЫЕИ ЯРПНЙЕ, МЮОПХЛЕП:
              SELECT    sal,
                        Job,
                        ename,
                        dept
              FROM      emp
              WHERE     sal > any
                        (SELECT   sal
                        FROM emp
                        WHERE deptno = 30)
              ORDER BY  sal;
  4. яРПНЙХ, ЙНРНПШЕ МЕ МЮВХМЮЧРЯЪ Я ОПХБЕДЕММШУ БШЬЕ ЙКЧВЕБШУ ЯКНБ ЯКЕДСЕР МЮВХМЮРЭ Я ОНГХЖХХ БРНПНЦН ЯКНБЮ Б ОПЕДШДСЫЕИ ЯРПНЙЕ, МЮОПХЛЕП:
              SELECT    ename,
                        dept
              FROM      emp

2.3 йНМЯРЮМРШ Х ОЕПЕЛЕММШЕ

  1. йНМЯРЮМРШ, ОЕПЕЛЕММШЕ Х Р.О. ЯКЕДСЕР ПЮЯОНКЮЦЮРЭ Я ОПЮБНИ ЯРНПНМШ НР ЯКНБ WHERE ХКХ HAVING.
          SELECT    ename
          FROM      emp
          WHERE     empno = '1232'

          Or

          SELECT    ename
          FROM      emp
          WHERE     empno = :1

2.4 бМЕЬМХЕ НАЗЕДХМЕМХЪ (outer joins)

оНКЪ, ЙНРНПШЕ БНБКЕЙЮЧРЯЪ Б НОЕПЮЖХЧ БМЕЬМЕЦН НАЗЕДХМЕМХЪ (outer join) ЯКЕДСЕР ОХЯЮРЭ Я ОПЮБНИ ЯРНПНМШ НР ЯКНБ WHERE ХКХ HAVING.

          SELECT    ename
          FROM      emp e,
                    dept d
          WHERE     e.empno = d.empno(+)

2.5 яХМНМХЛШ РЮАКХЖ (aliases)

яХМНМХЛШ ДКЪ РЮАКХЖ ЯКЕДСЕР ОПХЛЕМЪРЭ БН БЯЕУ ГЮОПНЯЮУ, Б ЙНРНПШУ СОНЛХМЮЕРЯЪ АНКЭЬЕ НДМНИ РЮАКХЖШ Б ОПЕДКНФЕМХХ FROM. хЯОНКЭГНБЮМХЕ ЯХМНМХЛНБ (alias) Б РЮЙХУ ГЮОПНЯЮУ СЯЙНПЪЕР НОЕПЮЖХЧ ПЮГАНПЮ SQL НОЕПЮРНПЮ ЪДПНЛ Oracle, ОНЯЙНКЭЙС СЛЕМЭЬЮЕР ПЕЙСПЯХЧ ГЮОПНЯНБ.

          SELECT    count(*)
          FROM      oe o,
                    oe_link l,
                    oe_link_name n
          WHERE     o.oe = l.oe
          AND       l.name = n.name

нРЛЕРЭРЕ, ВРН ЯХМНМХЛШ o, l, n ХЯОНКЭГСЧРЯЪ Б ОПЕДКНФЕМХХ WHERE.

2.6 оНПЪДНЙ СЯКНБХИ Б ОПЕДКНФЕМХХ WHERE

б ЖЕКЪУ НАКЕЦВЕМХЪ ВХРЮЕЛНЯРХ Х ОНМХЛЮМХЪ ГЮОПНЯЮ Б ОПЕДКНФЕМХХ WHERE ЯКЕДСЕР ЯМЮВЮКЮ ОХЯЮРЭ СЯКНБХЪ НАЗЕДХМЪЧЫХЕ РЮАКХЖШ, Ю ОНРНЛ СЯКНБХЪ НЦПЮМХВХБЮЧЫХЕ БШАНПЙС.

3.0 гЮОПНЯШ Й ад

3.1 оНПЪДНЙ ОЕПЕВХЯКЕМХЪ РЮАКХЖ Б ОПЕДКНФЕМХХ FROM

оНПЪДНЙ ОЕПЕВХЯКЕМХЪ РЮАКХЖ Б ОПЕДКНФЕМХХ FROM ХЛЕЕР ГМЮВЕМХЕ ДКЪ НОРХЛХГЮРНПЮ, ЙНЦДЮ НОРХЛХГЮРНП БШАХПЮЕР ЯОНЯНА БШОНКМЕМХЪ ГЮОПНЯЮ. нОРХЛХГЮРНП ПЮАНРЮЕР ЯКЕДСЧЫХЛ НАПЮГНЛ. нМ ОПНЯЛЮРПХБЮЕР ОПЕДКНФЕМХЪ WHERE Х ОПХЯБЮХБЮЕР РЮАКХЖЮЛ НОПЕДЕКЕММШИ БЕЯ, НЯМНБШБЮЪЯЭ МЮ РХОЕ ОПЕДХЙЮРЮ, Р.Е. field = 'const' ХКХ field = field(+). гЮРЕЛ НМ БШАХПЮЕР РЮАКХЖС Я МЮХЛЕМЭЬХЛ БЕЯНЛ Х ДЕКЮЕР ЕЕ СОПЮБКЪЧЫЕИ (driving) РЮАКХЖЕИ. нДМЮЙН, ГДЕЯЭ ЕЯРЭ НДХМ РНМЙХИ ЛНЛЕМР, ЕЯКХ МЕЯЙНКЭЙН РЮАКХЖ ОНКСВЮЧР НДХМЮЙНБШИ БЕЯ Х НМ ЪБКЪЕРЯЪ МЮХЛЕМЭЬХЛ, РН НОРХЛХГЮРНП БШАХПЮЕР Б ЙЮВЕЯРБЕ СОПЮБКЪЧЫЕИ РС РЮАКХЖС, ЙНРНПЮЪ ЯРНХР ОНЯКЕДМЕИ Б ОПЕДКНФЕМХХ FROM.

яОХЯНЙ БЕЯНБШУ ЙНЩЩТХЖХЕМРНБ ОПЕДХЙЮРНБ ОПХБЕДЕМ Б ОПХКНФЕМХХ A.

пЮЯЯЛНРПХЛ ЯКЕДСЫХИ ОПХЛЕП.

          Indexes :

          unique on oe(id)
          unique on oe_link(oe)
          unique on oe_link_name(name)
          non unique on oe(oe)
        -------------------------------------

          SELECT    count(*)
          FROM      oe_link l,
                    oe_link_name n,
                    oe o
          WHERE     o.oe = l.oe
          AND       l.name = n.name

          Time 621.21 secs

          SELECT    count(*)
          FROM      oe o,
                    oe_link l,
                    oe_link_name n
          WHERE     o.oe = l.oe
          AND       l.name = n.name


          Time 197.05 secs

йЮЙ ЛШ БХДХЛ, БПЕЛЪ БШОНКМЕМХЪ ГЮОПНЯНБ ПЮГКХВЮЕРЯЪ. еДХМЯРБЕММНЕ ПЮГКХВХЕ Б ЩРХУ ДБСУ ГЮОПНЯЮУ ЯНЯРНХР Б ОНПЪДЙЕ ОЕПЕВХЯКЕМХЪ РЮАКХЖ Б ОПЕДКНФЕМХХ FROM. оНЩРНЛС ОНЯКЕДМЕИ Б ЯОХЯЙЕ ДНКФМЮ АШРЭ РЮАКХЖЮ, БНГБПЮЫЮЧЫЮЪ МЮХЛЕМЭЬЕЕ ЙНКХВЕЯРБН ЯРПНЙ.

3.2 мЕОПЕДМЮЛЕПЕММНЕ ГЮОПЕЫЕМХЕ ХМДЕЙЯНБ

яСЫЕЯРБСЕР НВЕМЭ ОПНЯРНИ ОСРЭ МЕОПЕДМЮЛЕПЕММН ХЯЙКЧВХРЭ ХЯОНКЭГНБЮМХЕ ХМДЕЙЯНБ Б ГЮОПНЯЮУ.

On table oe, which is described in the б РЮАКХЖЕ OE, ЙНРНПЮЪ НОХЯЮМЮ Б ОПХКНФЕМХХ я, ОНКЕ id ХЛЕЕР РХО NUMBER.

          SELECT    id,
                    oe
          FROM      oe
          WHERE     to_char(id) = 1232

          Time 97 secs.

          Б РН БПЕЛЪ, ЙЮЙ

          SELECT    id,
                    oe
          FROM      oe
          WHERE     id = 1232

          Time .4 secs.

оПХВХМНИ ФЕ ЪБКЪЕРЯЪ РН, ВРН Oracle МЕ ЛНФЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯ ЕЯКХ РХО ДЮММШУ ОНКЪ ХГЛЕМЪЕРЯЪ Б ОПЕДКНФЕМХХ WHERE. оПХЙКЮДМНЛС ОПНЦПЮЛЛХЯРС ЯКЕДСЕР СДНЯРНБЕПХРЭЯЪ, ВРН ОНКЪ Б ОПЕДКНФЕМХХ WHERE МЕ ХГЛЕМЪЧРЯЪ ЙЮЙХЛ КХАН ЯОНЯНАНЛ.

б ЯКЕДСЧЫЕЛ ОПХЛЕПЕ ХМДЕЙЯШ РЮЙФЕ МЕ ХЯОНКЭГСЧРЯЪ.

          SELECT    id,
                    oe
          FROM      oe
          WHERE     id+1 = 1233

хЯОНКЭГНБЮМХЕ РХОЮ ДЮММШУ DATE Б ОПЕДКНФЕМХХ WHERE ВЮЯРН ОПХБНДХР Й ОПНАКЕЛЮЛ. мЮОПХЛЕП, БШАПЮРЭ ГЮОХЯХ ЯДЕКЮММШЕ Б НОПЕДЕКЕММШИ ДЕМЭ ЛНФМН ЯКЕДСЧЫХЛХ РПЕЛЪ ЯОНЯНАЮЛХ.

          SELECT    *
          FROM      oe
          WHERE     trunc(timestamp) = '26-MAR-91'

          SELECT    *
          FROM      oe
          WHERE     timestamp between '26-mar-91'
          AND       '27-mar-91'

          SELECT    *
          FROM      oe
          WHERE     timestamp >= to_date('26-mar-91:00:00',
                    'dd-mon-yy:hh24:mi')
          AND       timestamp < to_date('27-mar-91:00:00',
                    'dd-mon-yy:hh24:mi')

оЕПБШИ ГЮОПНЯ АСДЕР БШОНКМЪРЭЯЪ 240 ЯЕЙСМД.

бШОНКМЕМХЕ БРНПНЦН ГЮОПНЯЮ ГЮИЛЕР БЯЕЦН 1.05 ЯЕЙСМДШ, НДМЮЙН НМ ХЛЕЕР МЕЙНРНПСЧ НЯНАЕММНЯРЭ. б ПЕГСКЭРЮРШ БШАНПЙХ ОНОЮДСР ЯРПНЙХ, ББЕДЕММШЕ Б ОНКМНВЭ 27 ЛЮПРЮ.

рПЕРХИ ГЮОПНЯ АСДЕР БШОНКМЪРЭЯЪ БЯЕЦН 0.5 ЯЕЙСМДШ Х НМ МЕ АСДЕР БШАХПЮРЭ ГЮОХЯХ ЯНГДЮММШЕ Б ОНКМНВЭ.

б ОПХБДЕММШУ МХФЕ ОПХЛЕПЮУ РЮЙФЕ ХЯОНКЭГСЕРЯЪ ЛНДХТХЙЮЖХЪ РХОЮ ДЮММШУ ОНКЪ. рЮЙХЛ НАПЮГНЛ, ЙНМЙЮРЕМЮЖХЪ ОНКЕИ ОПХБНДХР Й РНЛС, ВРН Oracle МЕ ХЯОНКЭГСЕР ХМДЕЙЯ ОН ЩРНЛС ОНКЧ.

оПХЛЕП a) ЯКЕДСЕР ОЕПЕОХЯЮРЭ ЙЮЙ ОПХЛЕП b)

          a)

          SELECT    *
          FROM      job
          WHERE     db_id||job_no = 'AZ0100201'

          b)

          SELECT    *
          FROM      job
          WHERE     db_id = 'AZ'
          AND       job_no  = '0100201'

пЮГПЮАНРВХЙЮЛ ЯКЕДСЕР ОПХМХЛЮРЭ БН БМХЛЮМХЕ, ВРН ОПХ ПЮГАНПЕ SQL НОЕПЮРНПЮ Oracle МЕЪБМН БШОНКМЪЕР ОПЕНАПЮГНБЮМХЕ РХОЮ ДЮММШУ. Oracle ОНФЕР БШАПЮРЭ ОПЕНАПЮГНБЮМХЕ РХОЮ ДЮММШУ ЙЮЙ ДКЪ ОНКЪ, РЮЙ Х ДКЪ ЙНМЯРЮМРШ. еЯКХ Oracle ПЕЬХР ОПЕНАПЮГНБЮРЭ РХО ДЮММШУ ОНКЪ, РН НМ МЕ АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯ ОН ЩРНЛС ОНКЧ. б МХФЕОПХБЕДЕММНИ РЮАКХЖЕ ОПХБЕДЕМШ ОПЮБХКЮ, ОН ЙНРНПШЛ Oracle БШАХПЮЕР ВРН ОПЕНАПЮГНБШБЮРЭ.

          Mixed               Common         Function
          datatype            Unit           chosen
          --------------      -----------    --------

          Char with number    number         to_number
          Char with rowid     rowid          to_rowid
          Char with date      date           to_date

яКЕДСЧЫХИ ОПХЛЕП ОНЙЮГШБЮЕР ЙЮЙ ЩРХ ОПЮБХКЮ ПЮАНРЮЧР МЮ ОПЮЙРХЙЕ.

          SELECT    deptno
          FROM      dept
          WHERE     deptno = 1324

          indexes

          non unique index on deptno

щРНР SELECT МЕ АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯШ, ОНРНЛС ВРН ОНКЕ deptno АСДЕР ОПЕНАПЮГНБШБЮРЭЯЪ ЪДПНЛ Oracle Й РХОС NUMBER.

ю ЩРХ SELECT'Ш АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯ.

          SELECT    deptno
          FROM      dept
          WHERE     deptno = to_char(1324)

          SELECT    deptno
          FROM      dept
          WHERE     deptno = '1324'

3.3 мЮЛЕПЕММНЕ ГЮОПЕЫЕМХЕ ХЯОНКЭГНБЮМХЪ ХМДЕЙЯНБ

б МЕЙНРНПШУ ЯКСВЮЪУ БНГМХЙЮЕР МЕНАУНДХЛНЯРЭ ГЮОПЕРХРЭ ясад ХЯОНКЭГНБЮРЭ ХМДЕЙЯШ. дКЪ ЩРХУ ЖЕКЕИ ЛНФМН ХЯОНКЭГНБЮРЭ ЯКЕДСЧЫХЕ ЛНДХТХЙЮРНПШ.

          Datatype       Inhibit expression
          --------       ------------------

          Char           char||''
          number         number+0
          date           add_months(date,0)

оПХЛЕМЕМХЕ nvl(column,0) БНГЛНФМН ЯН БЯЕЛХ РХОЮЛХ ДЮММШУ, НДМЮЙН, Б МЕЙНРНПШУ ЯКСВЮЪУ ЩРН ЛНФЕР ОПХБЕЯРХ Й БШОНКМЕМХЧ ЛМНФЕЯРБЮ МЕМСФМШУ ЛЮРЕЛЮРХВЕЯЙХУ НОЕПЮЖХИ, ЯЛ. ЯКЕДСЧЫХИ ОПХЛЕП.

          SELECT    deptno
          FROM      dept
          WHERE     nvl(deptno,0) = '1234'

3.4 пЮГКХВМШЕ БЮПХЮМРШ МЮОХЯЮМХЪ ГЮОПНЯНБ

SQL НВЕМЭ БШПЮГХРЕКЭМШИ ЪГШЙ Х НАШВМН ЯСЫЕЯРБСЕР МЕЯЙНКЭЙН БЮПХЮМРНБ БШОНКМЕМХЪ НДМНЦН Х РНЦН ФЕ ГЮОПНЯЮ. пЮГПЮАНРВХЙЮЛ ЯКЕДСЕР ХЯЯКЕДНБЮРЭ ПЮГКХВМШЕ БЮПХЮМРШ МЮОХЯЮМХЪ ГЮОПНЯНБ Я ЖЕКЭЧ БШАНПЮ МЮХКСВЬЕЦН.

оПНДЕЛНМЯРПХПСЕЛ ЩРН МЮ ЯКЕДСЧЫЕЛ ОПХЛЕПЕ, ОСЯРЭ МЮЛ МЮДН МЮИРХ ВЕКНБЕЙЮ, ЙНРНПШИ МЕ ХЛЕЕР ГЮДЮМХЪ. б ад ХЛЕЕРЯЪ 99 ВЕКНБЕЙ Х 9900 ГЮДЮМХИ.

б НАЕХУ РЮАКХЖЮУ ЯНГДЮМШ ХМДЕЙЯШ ОН ОНКЧ name.

оЕПБШИ БЮПХЮМР

          SELECT    p.name
          FROM      people p,
                    job j
          WHERE     p.name = j.name(+)
          AND       j.name is null

          fred the 27

          1 record selected.

          Time 51.40 secs.

мЕ НВЕМЭ УНПНЬЕЕ БПЕЛЪ БШОНКМЕМХЪ.

бРНПНИ БЮПХЮМР

          SELECT    name
          FROM      people
          WHERE     name not in
                    (SELECT   name
                     FROM     job)

          fred the 27

          1 record selected.

          Time 6.11 secs

цНПЮГДН КСВЬХИ ПЕГСКЭРЮР, БПЕЛЪ БШОНКМЕМХЪ СЛЕМЭЬЕМН ОНВРХ МЮ ОНПЪДНЙ! лШ ЛНЦКХ АШ ОНВХБЮРЭ МЮ КЮБПЮУ, ОХРЭ ВЮИ ГЮДПЮБ МНЦХ ББЕПУ, НДМЮЙН, ЕЯКХ ЛШ ОНДОПЮБХЛ ОНДГЮОПНЯ...

          SELECT    name
          FROM      people p
          where     not name in
                    (SELECT   name
                    FROM      job j
                       WHERE     p.name = j.name)

          fred the 27

          1 record selected.

          Time 1.08 secs.

:-)

3.5 хЯОНКЭГНБЮМХЕ НОЕПЮРНПЮ EXISTS

нДХМ ХГ НОЕПЮРНПНБ, ЙНРНПШИ ВЮЯРН ХЦМНПХПСЕРЯЪ ЩРН НОЕПЮРНП EXISTS. нМ ЛНФЕР АШРЭ ХМНЦДЮ ОНКЕГЕМ ДКЪ БНБКЕВЕМХЪ БМЕЬМХУ ЙКЧВЕИ (foreign keys). б ЯКЕДСЧЫЕЛ ОПХЛЕПЕ ЛШ ОПНБЕПЪЕЛ ХЛЕР КХ 'fred the 45' ЙЮЙНЕ-КХАН ГЮДЮМХЕ.

оЕПБШИ БЮПХЮМР

          SELECT    distinct 'x'
          FROM      job
          WHERE     name = 'fred the 45'

          1 record selected.

          Time  0.45 secs.

бН БРНПНЛ БЮПХЮМРЕ ЛШ ХЯОНКЭГСЕЛ НОЕПЮРНП EXISTS Х ОНКСВЮЕЛ СЛЕМЭЬЕМХЕ БПЕЛЕМХ НАПЮАНРЙХ ОНВРХ Б ДБЮ ПЮГЮ.

          SELECT    'x'
          FROM      dual
          WHERE     exists
                    ( SELECT  'x'
                    FROM      job
                    where     name = 'fred the 45')

          1 record selected.

          Time 0.26 secs.

оПХВХМЮ СЯЙНПЕМХЪ НАПЮАНРЙХ ЯНЯРНХР Б РНЛ, ВРН ЪДПН Oracle ГМЮЕР, ВРН ЛНФМН НЯРЮМНБХРЭЯЪ ОНЯКЕ РНЦН, ЙЮЙ МЮИДЕМН УНРЪ АШ НДМН ЯНБОЮДЕМХЕ name = 'fred the 45'. оНЩРНЛС Oracle МЕ АСДЕР ОПНЯЛЮРПХБЮРЭ БЯЧ РЮАКХЖС ЖЕКХЙНЛ.

яРЮМНБХРЯЪ ХМРЕПЕЯМЕЕ, РЕОЕПЭ БХДМН, ВРН НАЗЕЛ ХГБКЕЙЮЕЛШУ ДЮММШУ НОПЕДЕКЪЕР ЙЮЙНИ ГЮОПНЯ МЮДН ХЯОНКЭГНБЮРЭ. пЮЯЯЛНРПХЛ ЯХРСЮЖХЧ, ЙНЦДЮ РЮАКХЖЮ people ХЛЕЕР 10,000 ГЮОХЯЕИ.

гЮОПНЯШ Н 'fred the 34' Х 'fred the 9999' ДЮЧР ЯКЕДСЧЫХЕ ПЕГСКЭРЮРШ.

          SELECT    distinct 'x'
          FROM      job
          WHERE     name ='fred the 34'

          Time 6.65 secs.


          SELECT    'x'
          FROM      dual
          WHERE     exists
                    (SELECT   'x'
                    FROM      job
                    WHERE     name = 'fred the 34')

          Time 0.28 secs.


          SELECT    'x'
          FROM      dual
          WHERE     exists
                    (SELECT 'x'
                    FROM job
                    WHERE name = 'fred the 9999')

          Time 8.28 secs.

щРН ОПНХЯУНДХР ХГ-ГЮ РНЦН, ВРН ДЮММШЕ Б РЮАКХЖЕ УПЮМЪРЯЪ ОН ОНПЪДЙС, УНРЪ Б НАЫЕЛ ЯКСВЮЕ ЩРН МЕ РЮЙ. б ДЮММНЛ ЯКСВЮЕ ГЮОХЯЭ 'fred the 1' МЮУНДХРЯЪ Б ОЕПБНЛ АКНЙЕ РЮАКХЖШ, Ю ГЮОХЯЭ 'fred the 9999' Б ОНЯКЕДМЕЛ АКНЙЕ.

пЮГПЮАНРВХЙЮЛ ЯКЕДСЕР ХЛЕРЭ Б БХДС, ВРН ЩТТЕЙРХБМНЯРЭ НОЕПЮРНПНБ EXISTS Х IN ГЮБХЯХР НР НР ЙНКХВЕЯРБЮ ДЮММШУ Б ЙЮФДНИ ХГ РЮАКХЖ, ГЮДЕИЯРБНБЮММШУ Б ГЮОПНЯЕ. б ГЮОПНЯЕ Я ХЯОНКЭГНБЮМХЕЛ IN СОПЮБКЪЧЫЕИ РЮАКХЖЕИ ЪБКЪЕРЯЪ ОНДГЮОПНЯ СЙЮГЮММШИ Б IN(), НЯМНБМНИ ГЮОПНЯ ОНБРНПЪЕРЯЪ ДКЪ ЙЮФДНИ ЯРПНЙХ БНГБПЮЫЮЕЛНИ ОНДГЮОПНЯНЛ Б IN(). б ГЮОПНЯЕ Я ХЯОНКЭГНБЮМХЕЛ EXISTS МЮНАНПНР, СОПЮБКЪЧЫХЛ ЪБКЪЕРЯЪ НЯМНБМНИ ГЮОПНЯ, Х ОНДГЮОПНЯ СЙЮГЮММШИ Б EXISTS() ОНБРНПЪЕРЯЪ ДКЪ ЙЮФДНИ ЯРПНЙХ, БШАХПЮЕЛНИ Б НЯМНБМНЛ ГЮОПНЯЕ. рЮЙХЛ НАПЮГНЛ, ЕЯКХ ОНДГЮОПНЯ БНГБПЮЫЮЕР ЛЮКНЕ ЙНКХВЕЯРБН ЯРПНЙ, Ю НЯМНБМНИ ГЮОПНЯ БНГБПЮЫЮЕР АНКЭЬНЕ ЙНКХВЕЯРБН ЯРПНЙ ОПХВЕЛ ДКЪ ЙЮФДНИ ХГ ЯРПНЙ ОНКСВЕММШУ Б ОНДГЮОПНЯЕ, РН ЯКЕДСЕР ХЯОНКЭГНБЮРЭ НОЕПЮРНП IN.

3.6 мЕ ДЕКЮИРЕ МЕМСФМШУ НАЗЕДХМЕМХИ (joins)

б МЕЙНРНПШУ ОПНДСЙРЮУ, ОПХЛЕМЪЕЛШУ Б МЮЬЕИ НПЦЮМХГЮЖХХ, ПЮГПЮАНРВХЙХ ДЕКЮЧР НАЗЕДХМЕМХЪ (joins) Я ЯХЯРЕЛМНИ РЮАКХЖЕИ sys_param. щРН МЕОПЮБХКЭМШИ ОНДУНД Х НМ ДНКФЕМ АШРЭ ХЯЙНПЕМЕМ. рЮАКХЖЮ sys_param ОПЕДМЮГМЮВЕМЮ ДКЪ ОНДДЕПФЙХ ЯХЯРЕЛШ, Х ЯНДЕПФХР НАЫЕЯХЯРЕЛМШЕ ЙНМЯРЮМРШ.

оПЮБХКЭМШЛ ОНДУНДНЛ Й ХЯОНКЭГНБЮМХЧ ЩРНИ РЮАКХЖШ ЪБКЪЕРЯЪ ХГБКЕВЕМХЕ ХГ МЕЕ МЕНАУНДХЛШУ ГМЮВЕМХИ НДХМ ПЮГ Б МЮВЮКЕ ОПНЦПЮЛЛШ, ХКХ, Б ЯКСВЮЕ БШОНКМЕМХЪ ПЕЦСКЪПМШУ ЖХЙКНБ НАМНБКЕМХИ, Б МЮВЮКЕ ЙЮФДНЦН РЮЙНЦН ЖХЙКЮ.

мЮ КНЦХВЕЯЙНЛ СПНБМЕ КЧАЮЪ ЛНДХТХЙЮЖХЪ РЮАКХЖШ sys_param БН БПЕЛЪ БШОНКМЕМХЪ ОПНЦПЮЛЛШ СЙЮГШБЮЕР МЮ БНГЛНФМН ОПНОСЫЕММШЕ ДЮММШЕ.

3.7 пЕЯСПЯНЕЛЙХЕ НОЕПЮЖХХ

гЮОПНЯШ, ЯНДЕПФЮЫХЕ НОЕПЮРНПШ DISTINCT, UNION, MINUS, INTERSECT, ORDER BY ХКХ GROUP BY ГЮЯРЮБКЪЧР ЪДПН Oracle БШОНКМЪРЭ ПЕЯСПЯНЕЛЙСЧ НОЕПЮЖХЧ ЯНПРХПНБЙХ. нОЕПЮРНП DISTINCT РПЕАСЕР БШОНКМХРЭ НДМС НОЕПЮЖХЧ ЯНПРХПНБЙХ, ДПСЦХЕ НОЕПЮРНПШ ГЮЯРЮБКЪЧР ЪДПН БШОНКМХРЭ ЙЮЙ ЛХМХЛСЛ ДБЕ НОЕПЮЖХХ ЯНПРХПНБЙХ. бЯЕЦДЮ ЯКЕДСЕР ХЯЙЮРЭ ДПСЦХЕ ОСРХ БШОНКМЕМХЪ ОНДНАМШУ ГЮОПНЯНБ. аНКЭЬХМЯРБН ГЮОПНЯНБ ЯНДЕПФЮЫХУ UNION, MINUS Х INTERSECT ЛНЦСР АШРЭ БШОНКМЕМШ ХМШЛ ЯОНЯНАНЛ.

3.8 хЯОНКЭГСИРЕ ДКЪ РЕЯРНБ ПЕЮКЭМШЕ ДЮММШЕ

дКЪ РЕЯРХПНБЮМХЪ ОПНЦПЮЛЛ Х ГЮОПНЯНБ БЯЕЦДЮ ЯКЕДСЕР ХЯОНКЭГНБЮРЭ МЮАНП ДЮММШУ АКХГЙХИ Й ПЕЮКЭМНЛС ЙЮЙ ОН НАЗЕЛС, РЮЙ Х ОН ГМЮВЕМХЪЛ, СЙЮГЮММШЛ Б ER ДХЮЦПЮЛЛЕ.

мХФЕ ОПХБЕДЕММШЕ БШЙКЮДЙХ ЯДЕКЮМШ МЮ АЮГЕ ОПХЛЕПЮ, ПЮЯЯЛНРПЕММНЦН Б ПЮГДЕКЕ 3.4. рЕОЕПЭ Б РЮАКХЖС people ЛШ ОНЛЕЯРХЛ 999 ГЮОХЯЕИ, Ю Б РЮАКХЖС job 9990 ГЮОХЯЕИ. дПСЦХЛХ ЯКНБЮЛХ ЛШ СБЕКХВХКХ МЮ ОНПЪДНЙ ЙНКХВЕЯРБН КЧДЕИ.

          SELECT    p.name
          FROM      people p,
                    job j
          WHERE     p.name = j.name(+)
          AND       j.name is null

          fred the 218

          Time 23.20 secs.


          SELECT    name
          FROM      people
          WHERE     not name in
                    (SELECT name
                    FROM job)

          fred the 218

          Time 193.46 secs.


          SELECT    name
          FROM      people p
          WHERE     not name in
                    (SELECT   name
                    FROM      job j
                    WHERE     p.name = j.name)

          fred the 218

          Time  8.66 secs.

йЮЙ БШ СФЕ ГЮЛЕРХКХ, БПЕЛЪ БШОНКМЕМХЪ ГЮОПНЯЮ, ХЯОНКЭГСЧЫЕЦН БМЕЬМЕЕ НАЗЕДХМЕМХЕ (outer join), ЛМНЦН ЛЕМЭЬЕ, ВЕЛ БПЕЛЪ БШОНКМЕМХЪ ГЮОПНЯЮ, ХЯОНКЭГСЧЫЕЦН ОНДГЮОПНЯ. р.Е. ЩРХ ПЕГСКЭРЮРШ ОНКМНЯРЭЧ ОПНРХБНОНКНФМШ ПЕГСКЭРЮРЮЛ ОНКСВЕММШЛ Б 3.4.

щРНР ОПХЛЕП БОНКМЕ ДНУНДВХБН ОНЙЮГШБЮЕР, ВРН ПЮГПЮАНРВХЙ ДНКФЕМ ГМЮРЭ ЙЮЙ ЯРПСЙРСПС ДЮММШУ, РЮЙ Х РХОХВМНЕ ДКЪ ГЮДЮВХ ЙНКХВЕЯРБН ЯРПНЙ Б ЙЮФДНИ РЮАКХЖЕ.

3.9 оПХЛЕМЕМХЕ НОЕПЮРНПЮ !=

хГАЕЦЮИРЕ ОПХЛЕМЪРЭ НОЕПЮРНП != БН БЯЕУ ЯКСВЮЪУ, ЙНЦДЮ ЛНФМН НАНИРХЯЭ АЕГ МЕЦН. оПХЛЕМЕМХЕ ЩРНЦН НОЕПЮРНПЮ НРЙКЧВЮЕР ХЯОНКЭГНБЮМХЕ ХМДЕЙЯНБ, ОНРНЛС ВРН ЪДПН Oracle ОНКЮЦЮЕР Б ЩРНЛ ЯКСВЮЕ, ВРН ГЮОПНЯ ХГБКЕЙЮЕР ОНВРХ БЯЕ ЯРПНЙХ РЮАКХЖШ.

3.10 хЯОНКЭГНБЮМХЕ Oracle trace

дКЪ ЙЮФДНЦН ГЮОПНЯЮ, ДЮЕФ ЕЯКХ НМ ЙЮФЕРЯЪ ОПНЯРЕИЬХЛ, ОПНБЕПЭРЕ ЕЦН ОКЮМ БШОНКМЕМХЪ Я ОНЛНЫЭЧ Oracle trace. оЕПБШЛ ЬЮЦНЛ Б НОРХЛХГЮЖХХ ГЮОПНЯЮ ДНКФМН АШРЭ ХЯЙКЧВЕМХЕ FTS - ОНКМНЦН ЯЙЮМХПНБЮМХЪ РЮАКХЖШ, ЩРН ЛНФЕР АШРЭ ЯДЕКЮМН Я ОНЛНЫЭЧ Oracle trace. яЛ. оПХКНФЕМХЕ F.

оПХЛЕВЮМХЕ:
дКЪ ОЕПБНМЮВЮКЭМНИ НОРХЛХГЮЖХХ ГЮОПНЯНБ ПЕЙНЛЕМДСЕРЯЪ ХЯОНКЭГНБЮРЭ ЙНЛЮМДС EXPLAIN PLAN. (нЯХОНБ д.л.)

3.11 сОПЮБКЕМХЕ ЙСПЯНПЮЛХ OraclЕ

бН БЯЕУ ЯКСВЮЪУ, ЙНЦДЮ ЩРН БНГЛНФМН, БЯЕ ЙСПЯНПШ, ХЯОНКЭГСЕЛШЕ Б ОПНЦПЮЛЛЕ, ДНКФМШ АШРЭ НОХЯЮМШ Б МЮВЮКЕ ОПНЦПЮЛЛШ. уНПНЬХЛ ЯРХКЕЛ ОПНЦПЮЛЛХПНБЮМХЪ ЯВХРЮЕРЯЪ ЯПЮГС Б МЮВЮКЕ ОПНЦПЮЛЛШ НАЗЪБХРЭ ЛЮЙЯХЛЮКЭМНЕ ЙНКХВЕЯРБН ЙСПЯНПНБ, ЙНРНПНЕ АСДЕР Б МЕИ ХЯОНКЭГНБЮРЭЯЪ. щРН ЛНФЕР АШРЭ ЯДЕКЮМН Б ясад ОНЯПЕДЯРБНЛ НРЙПШРХЪ БЯЕУ ЙСПЯНПНБ Б МЮВЮКЕ ОПНЦПЮЛЛШ, Ю Б Pro*C Х ДПСЦХУ ЪГШЙЮУ НОЕПЮРНПНЛ set MAXCURSORS.

бШОНКМЕМХЕ ГЮОПНЯЮ ЛНФМН ПЮГДЕКХРЭ МЮ РПХ ТЮГШ. оЕПБЮЪ ТЮГЮ ЩРН ЙНЛОХКЪЖХЪ ХКХ ПЮГАНП (parse) ГЮОПНЯЮ, БРНПЮЪ — ОНДЯРЮМНБЙЮ ГМЮВЕМХИ ОЕПЕЛЕММШУ (bind), Х РПЕРЭЪ БШАНПЙЮ ПЕГСКЭРЮРНБ (fetch). яКЕДСЕР ХЛЕРЭ Б БХДС, ВРН ОЕПБШЕ ДБЕ ТЮГШ НРМНЯХРЕКЭМН 'ДНПНЦХЕ', Р.Е. РПЕАСЧР АНКЭЬЕ ОПНЖЕЯЯНПМНЦН БПЕЛЕМХ.

вРН ФЕ ОПНХЯУНДХР БН БПЕЛЪ ЙНЛОХКЪЖХХ. бН БПЕЛЪ ЩРНИ ТЮГШ НАПЮАНРЙХ SQL ГЮОПНЯ, МЮОХЯЮММШИ ОПНЦПЮЛЛХЯРНЛ, ОПЕНАПЮГСЕРЯЪ БН БМСРПЕММЕЕ ОПЕДЯРЮБКЕМХЕ Б РЕ ЙНДШ, ЙНРНПШЕ БНЯОПХМХЛЮЧРЯЪ ЪДПНЛ Oracle. Oracle БШОНКМЪЕР ЯКЕДСЧЫХЕ ДЕИЯРБХЪ:

  1. ОПНЯЛЮРПХБЮЕР ЯКНБЮПЭ ДЮММШУ Х БШОНКМЪЕР ОПНБЕПЙС ОПЮБ ДНЯРСОЮ. дКЪ ЩРНЦН Oracle ЦЕМЕПХПСЕР МЕЯЙНКЭЙН SQL ГЮОПНЯНБ, ЙНРНПШЕ МЮГШБЮЧРЯЪ ПЕЙСПЯХБМШЛХ ГЮОПНЯЮЛХ (recursive queries), Я ОНЛНЫЭЧ ЙНРНПШИ ОПНБЕПЪЕР ХЛЕЕР КХ ДЮММШИ ОНКЭГНБЮРЕКЭ ОПЮБН ДНЯРСОЮ Й СЙЮГЮММНЛС ЯРНКАЖС Х Р.Д.
  2. НОРХЛХГХПСЕР ГЮОПНЯ. гДЕЯЭ БШОНКМЪЕРЯЪ РЮ НОРХЛХГЮЖХЪ, ЙНРНПЮЪ БШГБЮМЮ НАПЮЫЕМХЕЛ Й ОПЕДЯРЮБКЕМХЪЛ (view) Х БШОНКМЕМХЕЛ ОНДГЮОПНЯНБ.

оНЯЙНКЭЙС БШЬЕОЕПЕВХЯКЕММШЕ НОЕПЮЖХХ ГЮМХЛЮЧР НОПЕДЕКЕММНЕ БПЕЛЪ Х РПЕАСЧР ПЕЯСПЯНБ ОПНЖЕЯЯНПЮ, РН ГЮЯРЮБКЪРЭ Oracle БШОНКМЪРЭ ХУ МСФМН ЙЮЙ ЛНФМН ПЕФЕ.

бРНПЮЪ ТЮГЮ, ТЮГЮ ОНДЯРЮМНБЙХ (bind), БШОНКМЪЕРЯЪ ОНЯКЕ ЙНЛОХКЪЖХХ ГЮОПНЯЮ. бН БПЕЛЪ ЩРНИ ТЮГШ БШОНКМЪЕРЯЪ ОНДЯРЮМНБЙЮ ГМЮВЕМХЪ ОЕПЕЛЕММШУ Б ГЮОПНЯ. мЮОПХЛЕП, ОПХ НАПЮАНРЙЕ ГЮОПНЯЮ

         SELECT  'x'
         FROM    person 
         WHERE   name = :1 

ГМЮВЕМХЕ МЕЙНЕИ ОЕПЕЛЕММНИ 1 АСДЕР ОНДЯРЮБКЕМН Б ГЮОПНЯ ОН ЮДПЕЯС, ГЮПЕГЕПБХПНБЮММНЛС СЙЮГЮРЕКЕЛ :1.

б НАШВМШУ НАЯРНЪРЕКЭЯРБЮУ, ЦПЮЛНРМН МЮОХЯЮММЮЪ ОПНЦПЮЛЛЮ ДНКФМЮ ХЯОНКЭГНБЮРЭ ЯКЕДСЧЫХИ ЮКЦНПХРЛ ДКЪ ПЮАНРШ Я ГЮОПНЯНЛ, ЙНРНПШИ МЕНАУНДХЛН БШОНКМХРЭ АНКЕЕ НДМНЦН ПЮГЮ.

ьЮЦ 1

оПХ ГЮОСЯЙЕ ОПНЦПЮЛЛШ БШОНКМХРЭ НОПЕДЕКЕМХЕ Х ЙНЛОХКЪЖХЧ ГЮОПНЯЮ Я ОНЛНЫЭЧ БШГНБЮ ОПНЖЕДСП РХОЮ sql_set-up, open_cursor Х Р.О.

ьЮЦ 2

бШОНКМХРЭ ГЮОПНЯ ОЕПЕДЮБ ЕЛС ГМЮВЕМХЪ ЯННРБЕРЯРБСЧЫХУ ОЕПЕЛЕММШУ Я ОНЛНЫЭЧ БШГНБЮ ОПНЖЕДСП РХОЮ sql_execute, ora_bind Х Р.О.

ьЮЦ 3

хГБКЕВЭ Х НАПЮАНРЮРЭ ЯРПНЙХ, БНГБПЮЫЮЕЛШЕ ГЮОПНЯНЛ, Я ОНЛНЫЭЧ БШГНБЮ ОПНЖЕДСП РХОЮ sql_fetch, ora_fetch Х Р.О.

вРНАШ БШОНКМХРЭ ГЮОПНЯ ЕЫЕ ПЮГ — БЕПМСРЯЪ Й ЬЮЦС 2 ОНДЯРЮБХБ МНБШЕ ГМЮВЕМХЪ ОЕПЕЛЕММШУ.

3.12 оПЮБХКН 10,15,20 ОПНЖЕМРНБ

хЯОНКЭГНБЮМХЕ ХМДЕЙЯНБ Б ГЮОПНЯЮУ НОПЮБДЮМН, ЕЯКХ ГЮОПНЯ ХГБКЕЙЮЕР ЛЕМЭЬЕ 15% ЯРПНЙ ХГ РЮАКХЖШ. бН БЯЕУ НЯРЮКЭМШУ ЯКСВЮЪУ ОНКМШИ ОПНЯЛНРП РЮАКХЖШ (Full Table Scan FTS) АСДЕР ПЮАНРЮРЭ АШЯРПЕЕ.

щРН ОПЮБХКН МЮГШБЮЕРЯЪ ОПЮБХКНЛ 10,15,20 ОПНЖЕМРНБ, ОНРНЛС ВРН, Б ГЮБХЯХЛНЯРХ НР РНЦН ЙЮЙСЧ ДНЙСЛЕМРЮЖХЧ ОН Oracle БШ ВХРЮЕРЕ, БШ ЛНФЕРЕ БЯРПЕРХРЭ ЖХТПШ 10, 15 ХКХ 20 ОПНЖЕМРНБ.

4.0 нОЕПЮРНП INSERT

4.1 оПХЛЕМЕМХЕ * Б НОЕПЮРНПЕ INSERT

уНРЪ ОПХЛЕМЕМХЕ СЙНПНВЕММНИ МНРЮЖХХ Я ОПХЛЕМЕМХЕЛ ЯХЛБНКЮ '*' ДНОСЯЙЮЕРЯЪ ЪДПНЛ Oracle, РЮЙЮЪ ГЮОХЯЭ ЯВХРЮЕРЯЪ 'ОКНУХЛ РНМНЛ' Б ОПНЦПЮЛЛХПНБЮМХХ. рЮЙЮЪ ГЮОХЯЭ МЕ ДНОСЯЙЮЕРЯЪ Б МЮЬХУ ОПНЕЙРЮУ.

оПХВХМЮ ОН ЙНРНПНИ РЮЙЮЪ ГЮОХЯЭ ЯВХРЮЕРЯЪ 'ОКНУХЛ РНМНЛ' ЩКЕЛЕМРЮПМЮ — ЕЯКХ РЮАКХЖЮ, Б ЙНРНПСЧ ОПНХГБНДХРЯЪ INSERT, АСДЕР ЛНДХТХЖХПНБЮМЮ ОПХ ЙЮЙХУ-КХАН ЛНДХТХЙЮЖХЪУ АЮГШ ДЮММШУ, РН ОПНЦПЮЛЛЮ ОЕПЕЯРЮМЕР ПЮАНРЮРЭ.

5.0 нОЕПЮРНП UPDATE

5.1 яНЦКЮЯНБЮММШЕ ХГЛЕМЕМХЪ

нДМЮ ХГ МЮХАНКЕЕ ЛЕДКЕММШУ ЙНЛЮМД Б SQL ЩРН ЙНЛЮМДЮ UPDATE. щРН ЪБКЪЕРЯЪ ЯКЕДЯРБХЕЛ РНЦН, ВРН АНКЭЬХМЯРБН ЯНЦКЮЯНБЮММШУ ХГЛЕМЕМХИ Б РЮАКХЖЮУ РПЕАСЧР ОНКМНЦН ОПНЯЛНРПЮ РЮАКХЖ (FTS). б ПЕГСКЭРЮРЕ ЩРНЦН ЩРХ НОЕПЮЖХХ ЪБКЪЧРЯЪ ПЕЯСПЯНЕЛЙХЛХ Х НВЕМЭ ЛЕДКЕММШЛХ ЙНЦДЮ РЮАКХЖШ ЯКХЬЙНЛ АНКЭЬХЕ.

оПХБЕДЕММШИ МХФЕ НОЕПЮРНП UPDATE ЪБКЪЕРЯЪ РХОХВМШЛ ОПХЛЕПНЛ ЯНЦКЮЯНБЮММНЦН ХГЛЕМЕМХЪ.

  UPDATE target_table
  SET    target_field = (
                         SELECT source_information
                         FROM   source_table
                         WHERE  source_table.key = target_table.key
                         )
  WHERE  EXISTS (
                 SELECT 'x'
                 FROM   source_table
                 WHERE  source_table.key = target_table.key
                )

оПНАКЕЛЮ МХГЙНИ ОПНХГБНДХРЕКЭМНЯРХ БНГМХЙЮЕР ОНРНЛС, ВРН Б ГЮОПНЯЕ МЕ ХЯОНКЭГСЕРЯЪ ХМТНПЛЮЖХЪ ХГ source_table ДКЪ НЦЮМХВЕМХЪ ЙНКХВЕЯРБЮ ОПНЯЛЮРПХБЮЕЛШУ Б target_table ЯРПНЙ. еЯКХ ЙЮЙНЕ-КХАН СЯКНБХЕ Б ОПЕДКНФЕМХХ WHERE НОЕПЮРНПЮ UPDATE МЕ НРЯЕВЕР АНКЭЬХМЯРБН ЯРПНЙ ХГ target_table, РН ЩРНР НОЕПЮРНП UPDATE ОНРПЕАСЕР НЦПНЛМНЦН ЙНКХВЕЯРБЮ ОПНЖЕЯЯНПМНЦН БПЕЛЕМХ.

оПХБЕДЕММЮЪ МХФЕ PL/SQL ОПНЖЕДСПЮ ПЕЬЮЕР ЩРС ОПНАКЕЛС Х ЩТТЕЙРХБМН ХЯОНКЭГСЕР ХМДЕЙЯ ОН ОНКЧ key, ДКЪ РНЦН ВРНАШ БНБКЕВЭ Б ОПНЖЕЯЯ ХГЛЕМЕМХЪ НЦПЮМХВЕММНЕ ЙНКХВЕЯРБН ЯРПНЙ ХГ target_table.

   Declare
     CURSOR source IS
        SELECT *
        FROM   source_table;
   Begin
     FOR row IN source LOOP
       UPDATE target_table
       SET    target_field = row.source_information
       WHERE  key = row.key;
     END LOOP;
   Exception
     WHEN OTHERS THEN
     Null;
   End;

щРЮ PL/SQL ОПНЖЕДСПЮ ОПНЯЛЮРПХБЮЕР Б ЖХЙКЕ ГЮОХЯХ Б source_table Х ХГЛЕМЪЕР ЯННРБЕРЯРБСЧЫСЧ ЯРПНЙС Б target_table, Б РНЛ ЯКСВЮЕ ЕЯКХ НМЮ ЯСЫЕЯРБСЕР. оН ЯСРХ, ОПНЖЕДСПЮ ОЕПЕЙКЧВЮЕР ОНКМШИ ОПНЯЛНРП (FTS) Я РЮАКХЖШ target_table МЮ source_table Х ЩТТЕЙРХБМН ХЯОНКЭГСЕР ХМДЕЙЯ РЮАКХЖШ target_table.

бПЕЛЪ БШОНКМЕМХЪ БШЬЕОПХБЕДЕММНЦН НОЕПЮРНПЮ UPDATE, ЙНРНПШИ ХЯОПЮБКЪЕР 9 ГЮОХЯЕИ Б РЮАКХЖЕ ХЛЕЧЫЕИ 8000 ГЮОХЯЕИ ЯНЯРЮБКЪЕР 19.4 ЯЕЙСМДШ. рЕ ФЕ ЯЮЛШЕ ДЕИЯРБХЪ, БШОНКМЪЕЛШЕ Я ОНЛНЫЭЧ ОПНЖЕДСПШ МЮ PL/SQL ГЮМХЛЮЧР 1.12 ЯЕЙСМДШ, ДЮБЮЪ СКСВЬЕМХЕ ОПНХГБНДХРЕКЭМНЯРХ 94%.

PL/SQL ЯЙПХОР НДМНГМЮВМН АСДЕР БШХЦПШБЮРЭ Б ОПНХГБНДХРЕКЭМНЯРХ С НОЕПЮРНПЮ UPDATE ЙНЦДЮ РЮАКХЖЮ source_table ЛЕМЭЬЕ, ВЕЛ РЮАКХЖЮ target_table. оПХВЕЛ, ВЕЛ АНКЭЬЕ РЮАКХЖЮ target_table ОН ЯПЮБМЕМХЧ Я source_table, РЕЛ АНКЭЬЕ АСДЕР БШХЦПШЬ. еЯКХ ФЕ ЯСЫЕЯРБСЕР ХМДЕЙЯ ДКЪ РЮАКХЖШ target_table, ЙНРНПШИ ГМЮВХРЕКЭМН СЯЙНПЪЕР ОНХЯЙ ОН ЙКЧВС (WHERE key = row.key), РН ДКЪ ОПХБЕДЕММНИ БШЬЕ PL/SQL ОПНЖЕДСПШ ПЮГЛЕП РЮАКХЖШ target_table ОНВРХ МЕ НЙЮГШБЮЕР БКХЪМХЪ МЮ БПЕЛЪ БШОНКМЕМХЪ, ХЛЕЕР ГМЮВЕМХЕ РНКЭЙН ЙНКХВЕЯРБН ХГЛЕМЪЕЛШУ ЯРПНЙ.

б АНКЭЬХМЯРБЕ ЯКСВЮЕБ, ГЮЛЕМЮ ОПЕДКНФЕМХЪ EXISTS МЮ ОПЕДКНФЕМХЕ IN Б НОЕПЮРНПЕ UPDATE РЮЙФЕ ДЮЯР БШХЦПШЬ Б ЯЙНПНЯРХ БШОНКМЕМХЪ.

6.0 нОРХЛХГЮЖХЪ ГЮОПНЯНБ

6.1 дНЯРСО Й РЮАКХЖЮЛ

яСЫЕЯРБСЕР РПХ ЛЕРНДЮ, Я ОНЛНЬЭЧ ЙНРНПШУ Oracle ЛНФЕР МЮИРХ ЯРПНЙС Б РЮАКХЖЕ:

  1. оПНЯЛНРП БЯЕУ ЯРПНЙ Б РЮАКХЖЕ ОН ОНПЪДЙС Х ОПНБЕПЙЮ ЙЮФДНИ ЯРПНЙХ МЮ ЯННРБЕРЯРБХЕ ЙНМЙПЕРМНЛС СЯКНБХЧ. щРНР ЛЕРНД МЮГШБЮЕРЯЪ ОНКМНЕ ЯЙЮМХПНБЮМХЕ РЮАКХЖШ (full table scan, FTS), НМ ЪБКЪЕРЯЪ ЯЮЛШЛ ЛЕДКЕММШЛ Х МЮХЛЕМЕЕ ЩТТЕЙРХБМШЛ.
  2. хЯОНКЭГНБЮМХЕ ХМДЕЙЯЮ ДКЪ ОНХЯЙЮ ЯРПНЙХ.
  3. хЯОНКЭГНБЮМХЕ ХДЕМРХТХЙЮРНПЮ ЯРПНЙХ (ROWID) ДКЪ ОПЪЛНЦН ДНЯРСОЮ Й ЯРПНЙЕ. щРН МЮХАНКЕЕ ЩТТЕЙРХБМШИ ЛЕРНД ДНЯРСОЮ. нДМЮЙН, ЩРНР ЛЕРНД ЛНФМН ХЯОНКЭГНБЮРЭ РНКЭЙН Б ОПЕДЕКЮУ НДМНИ РПЮМГЮЙЖХ, ОНРНЛС ВРН ROWID ЛНФЕР ХГЛЕМХРЭЯЪ ОНЯКЕ ГЮБЕПЬЕМХЪ РПЮМГЮЙЖХХ, Х Б ЩРНЛ ЯКСВЮЕ ПЕЙНЛЕМДСЕРЯЪ ХЯОНКЭГНБЮРЭ ЛЕУЮМХГЛ ОЕПБХВМШУ ЙКЧВЕИ.

й ЯНФЮКЕМХЧ, ЛШ НАШВМН МЕ ГМЮЕЛ ROWID ЯРПНЙ РЮАКХЖШ, ОНЩРНЛС ЯЮЛШЛ АШЯРПШЛ ЛЕРНДНЛ ДНЯРСОЮ ЯКЕДСЕР ЯВХРЮРЭ ЛЕРНД Я ХЯОНКЭГНБЮМХЕЛ ХМДЕЙЯНБ.

Oracle АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯШ Б ЯКЕДСЧЫХУ ЯКСВЮЪУ:

  1. еЯКХ ОНКЕ, ОН ЙНРНПНЛС ЯСЫЕЯРБСЕР ХМДЕЙЯ, СОНЛЪМСРН Б ОПЕДКНФЕМХХ WHERE.
  2. еЯКХ ОНКЕ, ОН ЙНРНПНЛС ЯСЫЕЯРБСЕР ХМДЕЙЯ, МЕ ЛНДХТХЖХПСЕРЯЪ Б ГЮОПНЯЕ ЙЮЙНИ-КХАН ТСМЙЖХЕИ, ЛЮРЕЛЮРХВЕЯЙХЛ НОЕПЮРНПНЛ ХКХ Х РЕЛ Х ДПСЦХЛ ЯПЮГС. хЯЙКЧВЕМХЕ ЯНЯРЮБКЪЧР ЯКЕДСЧЫХЕ ЯКСВЮХ MIN(column), MIN(column+constant) MAX(column), MAX(column+constant).

Oracle МЕ АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯШ Б ЯКЕДСЧЫХУ ЯКСВЮЪУ:

  1. еЯКХ Б ГЮОПНЯЕ МЕР ОПЕДКНФЕМХЪ WHERE.
  2. еЯКХ ОНКЕ, ОН ЙНРНПНЛС ЯСЫЕЯРБСЕР ХМДЕЙЯ, ЛНДХТХЖХПСЕРЯЪ Б ГЮОПНЯЕ ЙЮЙХЛ-КХАН НАПЮГНЛ.
  3. еЯКХ БШОНКМЪЕРЯЪ ОНХЯЙ ДКЪ ГМЮВЕМХИ NULL ХКХ NOT NULL.

6.2 хМДЕЙЯШ Х NULL ГМЮВЕМХЪ

еЯКХ ОНКЕ, ОН ЙНРНПНЛС ЯНГДЮМ ХМДЕЙЯ, ОПХМХЛЮЕР ГМЮВЕМХЕ NULL Б ЙЮЙНИ-КХАН ЯРПНЙЕ РЮАКХЖШ, РН СЙЮГЮРЕКЭ МЮ ЩРС ЯРПНЙС МЕ БЙКЧВЮЕРЯЪ Б ХМДЕЙЯ. оН ЩРНИ ОПХВХМЕ Б ОПХБЕДЕММНЛ МХФЕ ГЮОПНЯЕ ХМДЕЙЯ ОН ОНКЧ COMM ХЯОНКЭГНБЮРЭЯЪ МЕ АСДЕР.

          SELECT    *
          FROM      emp
          WHERE     comm is NULL

оПХ БШОНКМЕМХХ ОНЙЮГЮММНЦН МХФЕ ГЮОПНЯЮ Oracle ОНКЮЦЮЕР, ВРН ДКЪ АНКЭЬХМЯРБЮ ГЮОХЯЕИ Б РЮАКХЖЕ EMP ОНКЕ COMM ХЛЕЕР ГМЮВЕМХЪ NOT NULL, Х ОНЩРНЛС МЕ АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯ, Ю БШОНКМХР ОНКМШИ ОПНЯЛНРП РЮАКХЖШ (FTS).

          SELECT    *
          FROM      emp
          WHERE     comm is not NULL

нДМЮЙН, FTS ЛНФЕР МЮЛ МЕ ОНДНИРХ, ЕЯКХ ЛШ ГМЮЕЛ, ВРН РЮЙХУ ГЮОХЯЕИ ЛЮКН. яКЕДСЧЫХИ ГЮОПНЯ ОЕПЕОХЯЮМ РЮЙХЛ НАПЮГНЛ, ВРНАШ ГЮЯРЮБХРЭ Oracle ХЯОНКЭГНБЮРЭ ХМДЕЙЯ ОН ОНКЧ COMM.

          SELECT    *
          FROM      emp
          WHERE     comm > -0.01

6.3 хМДЕЙЯШ Х ОПЕДХЙЮРШ 'NOT ='

йНЦДЮ ХЯОНКЭГСЕРЯЪ ОПЕДХЙЮР МЕ ПЮБМН ('!=', 'NOT =') Oracle МЕ АСДЕР ХЯОНКЭГНБЮРЭ ХМДЕЙЯ, НДМЮЙН ЕЯКХ ХЯОНКЭГСЧРЯЪ ДПСЦХЕ ОПЕДХЙЮРШ Я ОПХЯРЮБЙНИ NOT ХМДЕЙЯШ ХЯОНКЭГСЧРЯЪ, МЮОПХЛЕП:

          'not sal > 50' => 'sal <= 50'
          'not sal <= 50' => 'sal > 50'

6.4 оПЕДКНФЕМХЕ GROUP BY

яЙНПНЯРЭ БШОНКМЕМХЪ ГЮОПНЯНБ ЯНДЕПФЮЫХУ ОПЕДКНФЕМХЪ GROUP BY ЛНФЕР АШРЭ ГМЮВХРЕКЭМН ОНБШЬЕМЮ ОСРЕЛ ХЯЙКЧВЕМХЪ КХЬМХУ ЯРПНЙ ХГ НОЕПЮЖХХ ЦПСООХПНБЙХ. мХФЕ ОПХБЕДЕМШ ДБЮ ГЮОПНЯЮ, ЙНРНПШЕ БНГБПЮЫЮЧР РЕФЕ ЯЮЛШЕ ДЮММШЕ, НДМЮЙН БРНПНИ ГЮОПНЯ АСДЕР, ОНРЕМЖХЮКЭМН, БШОНКМЪРЭЯЪ АШЯРПЕЕ, РЮЙ ЙЮЙ ОПЕДКНФЕМХЕ WHERE НРЯЕВЕР МЕМСФМШЕ ЯРПНЙХ Х ЦПСООХПНБЙХ АСДЕР БШОНКМЪРЭЯЪ Я ЛЕМЭЬХЛ ЙНКХВЕЯРБНЛ ЯРПНЙ.

          SELECT    job,
                    avg(sal)
          FROM      emp
          GROUP BY  job
          HAVING    job = 'president'
          OR        job = 'manager'


          SELECT    job,
                    avg(sal)
          FROM      emp
          WHERE     job = 'president'
          OR        job = 'manager'
          GROUP BY  job

6.5 хЯОНКЭГНБЮМХЕ МЕЯЙНКЭЙХУ ХМДЕЙЯНБ

йНЦДЮ Б ГЮОПНЯЕ ЯСЫЕЯРБСЕР ДБЮ ХКХ АНКЕЕ ОПЕДХЙЮРЮ '=', РН Oracle ЛНФЕР ХЯОНКЭГНБЮРЭ ЯПЮГС МЕЯЙНКЭЙН ХМДЕЙЯНБ. бН БПЕЛЪ БШОНКМЕМХЪ ГЮОПНЯЮ Oracle ЯДЕКЮЕР ЯКХЪМХЕ (merge) ХМДЕЙЯНБ, Х БШАЕПЕР РЕ ЯРПНЙХ, МЮ ЙНРНПШЕ ЕЯРЭ ЯЯШКЙХ ЯПЮГС БН БЯЕУ ХМДЕЙЯЮУ. мЮОПХЛЕП:

          SELECT    ename
          FROM      emp
          WHERE     deptno=20
          AND       job='manager'

          АСДЕР БШОНКМЕМН ЯКХЪМХЕ ХМДЕЙЯНБ

          non unique index on job
          non unique index on deptno

6.6 йНЦДЮ МЕ БШОНКМЪЕРЯЪ ЯКХЪМХЕ ХМДЕЙЯНБ

б РЕУ ЯКСВЮЪУ, ЙНЦДЮ Б ГЮОПНЯЕ ХЯОНКЭГСЧРЯЪ ОПЕДХЙЮРШ '=' Х '<'/'>', ЙЮЙ Б МХФЕОПХБЕДЕММНЛ ГЮОПНЯЕ, Oracle МЕ ЛНФЕР БШОНКМХРЭ ЯКХЪМХЪ (merge) ХМДЕЙЯНБ. гДЕЯЭ АСДЕР ХЯОНКЭГНБЮРЭЯЪ ХМДЕЙЯ ОН ОНКЧ job ДКЪ РНЦН, ВРНАШ ОНКСВХРЭ ЯРПНЙХ Я job = 'manager', Ю ГЮРЕЛ ДКЪ ЩРХУ ЯРПНЙ АСДЕР БШОНКМЕМЮ ОПНБЕПЙЮ МЮ deptno > 10.

          SELECT    *
          FROM      emp
          WHERE     job='manager'
          AND       deptno > 10

          ХМДЕЙЯШ:

          non unique index on job
          non unique index on deptno

йНЦДЮ МЕКЭГЪ НРДЮРЭ ЪБМНЦН ОПЕДОНВРЕМХЪ ЙЮЙНЛС-КХАН ХМДЕЙЯС, ЙЮЙ Б МХФЕОПХБЕДЕММНЛ ГЮОПНЯЕ, Oracle АСДЕР ХЯОНКЭГНБЮРЭ РНКЭЙН НДХМ ХГ ХМДЕЙЯНБ, ОНЯЙНКЭЙС БШОНКМЪРЭ ХУ ЯКХЪМХЕ МЕ ЩТТЕЙРХБМН. гЮЛЕРЭРЕ, ВРН ОНБРНПМНЕ ЯЙЮМХПНБЮМХЕ (empno > 1) АСДЕР БШОНКМЕМН ДКЪ ЙЮФДНИ ЯРПНЙХ ОПНЬЕДЬЕИ ОЕПБСЧ ОПНБЕПЙС (sal > 1).

рЮЙ ЙЮЙ НАЮ ХМДЕЙЯЮ non unique, Oracle БШАЕПЕР РНР ХМДЕЙЯ, МЮ ЙНРНПШИ МЮРЙМЕРЯЪ ПЮМЭЬЕ Б РЮАКХЖЕ DC_INDEXES Б ЙЩЬЕ. ю ОНЯЙНКЭЙС ПЮГПЮАНРВХЙХ МЕ ГМЮЧР, ВРН ЯНДЕПФХРЯЪ Б ЙЩЬЕ, БШАНП ХМДЕЙЯЮ МЕ ОПЕДЯЙЮГСЕЛ.

          SELECT    ename
          FROM      emp
          WHERE     sal > 1
          AND       empno > 1

          ХМДЕЙЯШ:

          non unique index on empno
          non unique index on sal

6.7 оНДЮБКЕМХЕ ЯКХЪМХЪ ХМДЕЙЯНБ

йНЦДЮ ЕЯРЭ БШАНП ЛЕФДС ЯКХЪМХЕЛ (merge) unique ХМДЕЙЯЮ Я non unique ХМДЕЙЯНЛ ЪДПН Oracle БЯЕЦДЮ ХЯОНКЭГСЕР unique ХМДЕЙЯ Х ХГАЕЦЮЕР БШОНКМЪРЭ ЯКХЪМХЕ ХМДЕЙЯНБ. оПХВХМЮ ЩРНЦН ЯНЯРНХР Б РНЛ, ВРН unique ХМДЕЙЯ БНГБПЮЫЮЕР ЯЯШКЙС РНКЭЙН МЮ НДМС ЯРПНЙС. пЮЯЯЛНРПХЛ ЯКЕДСЧЫХИ ОПХЛЕП.

          SELECT    ename
          FROM      emp
          WHERE     sal = 3000
          AND       empno = 7902

          ХМДЕЙЯШ:

          unique index on empno
          non unique index on sal

гДЕЯЭ АСДЕР ХЯОНКЭГНБЮРЭЯЪ РНКЭЙН unique index on empno, ГЮРЕЛ, ЕЯКХ ГЮОХЯЭ МЮИДЕМЮ, АСДЕР БШОНКМЕМЮ ОПНБЕПЙЮ МЮ sal = 3000.

оПХ БШОНКМЕМХХ SQL НОЕПЮРНПЮ Oracle ЛНФЕР БШОНКМХРЭ ЯКХЪМХЕ МЕ АНКЕЕ 5-РХ ХМДЕЙЯНБ. нЯРЮКЭМШЕ ОПЕДХЙЮРШ АСДСР ОПНБЕПЪРЭЯЪ АЕГ ХЯОНКЭГНБЮМХЪ ХМДЕЙЯНБ.

          SELECT    *
          FROM      emp
          WHERE     empno =7844
          AND       job = 'salesman'
          AND       deptno = 30
          AND       sal = 1500
          AND       comm = 0
          AND       ename = 'turner'

          ХМДЕЙЯШ:

          non unique index on empno
          non unique index on job
          non unique index on deptno
          non unique index on sal
          non unique index on comm
          non unique index on ename

Because all the predicates score equally, according to APPENDIX A, only five of the above indexes will be used. Rows that are returned will be checked by the kernel to see if the last value is correct. оНЯЙНКЭЙС, ЯНЦКЮЯМН ОПХКНФЕМХЧ ю БЕЯ БЯЕУ ОПЕДХЙЮРНБ НДХМЮЙНБШИ, Oracle БШОНКМХР ЯКХЪМХЕ ХМДЕЙЯНБ. яНЦКЮЯМН СОНЛЪМСРШЛ БШЬЕ ОПЮБХКЮЛ, Oracle АСДЕР ХЯОНКЭГНБЮРЭ РНКЭЙН ОЪРЭ ХМДЕЙЯНБ ДКЪ ОНКСВЕМХЪ ЯЯШКЙХ МЮ ЯРПНЙС, ГЮРЕЛ ХГБКЕВЕР ЯРПНЙС ХГ ад Х ОПНБЕПХР ОНЯКЕДМЕЕ СЯКНБХЕ.

6.8 яНЯРЮБМШЕ ХМДЕЙЯШ

яНЯРЮБМШЛ МЮГШБЮЕРЯЪ ХМДЕЙЯ, ЙНРНПШИ ОНЯРПНЕМ ОН МЕЯЙНКЭЙХЛ ОНКЪЛ РЮАКХЖШ. Oracle ЛНФЕР ХЯОНКЭГНБЮРЭ ЯНЯРЮБМНИ ХМДЕЙЯ, ЕЯКХ Б ОПЕДКНФЕМХХ WHERE СЙЮГЮМН ОЕПБНЕ ХГ ОНКЕИ, ОН ЙНРНПШЛ ОНЯРПНЕМ ХМДЕЙЯ.

In the following examples assume a concatenated index on job and deptno. б ЯКЕДСЧЫЕЛ ОПХЛЕПЕ ЛШ ОНДПЮГСЛЕБЮЕЛ, ВРН ЯСЫЕЯРБСЕР ЯНЯРЮБМНИ ХМДЕЙЯ ... index on emp (job, deptno)

          SELECT    *
          FROM      emp
          WHERE     job = 'president'
          AND       deptno = 10

хМДЕЙЯ АСДЕР ХЯОНКЭГНБЮРЭЯЪ.

          SELECT    *
          FROM      emp
          WHERE     deptno = 10
          AND       job = 'president'

хМДЕЙЯ АСДЕР ХЯОНКЭГНБЮРЭЯЪ.

          SELECT    *
          FROM      emp
          WHERE     deptno = 10

хМДЕЙЯ МЕ АСДЕР ХЯОНКЭГНБЮРЭЯЪ, ОНРНЛС ВРН Б WHERE МЕР ЯЯШКЙХ МЮ job — ОЕПБНЕ ОНКЕ Б ЯНЯРЮБМНЛ ХМДЕЙЯЕ.

          SELECT    *
          FROM      emp
          WHERE     job = 'analyst'

б ЩРНЛ ЯКСВЮЕ АСДЕР ХЯОНКЭГНБЮРЭЯЪ ОЕПБЮЪ ВЮЯРЭ ХМДЕЙЯЮ. пЮГПЮАНРВХЙЮЛ ЯКЕДСЕР СВХРШБЮРЭ ЩРС НЯНАЕММНЯРЭ ОПХ ЯНГДЮМХХ ЯНЯРЮБМШУ ХМДЕЙЯНБ, ЛНФЕР РЮЙ ОНКСВХРЭЯЪ, ВРН ЯНЯРЮБМШЕ ХМДЕЙЯШ МЕ АСДСР ХЯОНКЭГНБЮРЭЯЪ.

          SELECT    *
          FROM      emp
          WHERE     job != 'clerk'
          AND       deptno = 10

хМДЕЙЯ МЕ АСДЕР ХЯОНКЭГНБЮРЭЯЪ, ОНРНЛС ВРН НОЕПЮРНП '!=' НРЙКЧВЮЕР ХЯОНКЭГНБЮМХЕ ХМДЕЙЯЮ. яЛ. ПЮГДЕК 3.9.

6.9 нОРХЛХГЮЖХЪ ГЮОПНЯНБ Я OR

б НРКХВХЕ НР НОЕПЮРНПЮ AND, ЙНРНПШИ РПЕАСЕР ВРНАШ ЯРПНЙЮ СДНБКЕРБНПЪКЮ НАНХЛ СЯКНБХЪЛ, НОЕПЮРНП OR РПЕАСЕР, ВРНАШ ЯРПНЙЮ СДНБКЕРБНПЪКЮ УНРЪАШ НДМНЛС СЯКНБХЧ. пЮЯЯЛНРПХЛ ЯКЕДСЧЫХИ ОПХЛЕП.

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     sal = 3000
          OR        job = 'clerk'

          ХМДЕЙЯ:

          non unique on job

еЯКХ ГДЕЯЭ ХЯОНКЭГНБЮРЭ ХМДЕЙЯ ОН ОНКЧ job, РН ЛШ ОНКСВХЛ РНКЭЙН РЕ ГЮОХЯХ Б ЙНРНПШУ job = 'clerk', Х ОПНОСЯРХЛ РЕ ГЮОХЯХ, Б ЙНРНПШУ job != 'clerk', МН sal = 3000, ВРН МЕ ЯННРБЕРЯРБСЕР СЯКНБХЪЛ ГЮОПНЯЮ.

хЯОНКЭГНБЮМХЕ ЯНЯРЮБМНЦН ХМДЕЙЯЮ ОН ОНКЪЛ (job, sal) ХКХ (sal, job) РЮЙФЕ МЕБНГЛНФМН, ОНЯЙНКЭЙС ГМЮВЕМХЪ ОНКЕИ ДНКФМШ ОПНБЕПЪРЭЯЪ МЕГЮБХЯХЛН ДПСЦ НР ДПСЦЮ.

еЯКХ С МЮЯ ЕЯРЭ ЯНЯРЮБМНИ ХМДЕЙЯ ОН (sal, job), РН ЪДПН Oracle ЛНФЕР БШОНКМХРЭ НОРХЛХГЮЖХЧ ГЮОПНЯЮ ОН ОНКЧ job. нОРХЛХГЮЖХХ ОНЛНФЕР РЮЙФЕ МЮКХВХЕ ОПНЯРНЦН ХМДЕЙЯЮ ОН ОНКЧ sal.

еЯКХ ФЕ ЯСЫЕЯРБСЧР ДБЮ ХМДЕЙЯЮ ОН НАНХЛ ОНКЪЛ, ЯБЪГЮММШЛ НОЕПЮРНПНЛ OR, РН ГЮОПНЯ АСДЕР ЙНМЖЕОРСЮКЭМН ОЕПЕЯЛНРПЕМ Х БШОНКМЕМ ЙЮЙ НАЗЕДХМЕМХЕ ДБСУ SQL НОЕПЮРНПНБ. пЮЯЯЛНРПХЛ ЩРН ОНДПНАМЕЕ.

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     sal = 3000
          OR        job = 'clerk'

          ХМДЕЙЯШ:

          non unique on job
          non unique on sal

яРЮМНБХРЯЪ:

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     job = 'clerk'

          UNION

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     sal = 3000
          AND       job != 'clerk'

гЮЛЕРЭРЕ, ВРН ЪДПН Oracle ХЯОНКЭГНБЮКН ОНЯКЕДМХИ ОПЕДХЙЮР Б ОПЕДКНФЕМХХ WHERE ДКЪ ЯНГДЮМХЪ ОЕПБНЦН ГЮОПНЯЮ Я ЕДХМЯРБЕММШЛ СЯКНБХЕЛ, Х ГЮРЕЛ ХЯОНКЭГНБЮКН РНР ФЕ ОПЕДХЙЮР, МН СФЕ Я НОЕПЮРНПНЛ '!=' БН БРНПНЛ ГЮОПНЯЕ Я ДБСЛЪ СЯКНБХЪЛХ. еЯКХ ЛШ ОЕПЕОХЬЕЛ ГЮОПНЯ ЯКЕДСЧЫХЛ НАПЮГНЛ:

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     job = 'clerk'
          OR        sal = 3000

          ХМДЕЙЯШ:

          non unique on job
          non unique on sal

яРЮМНБХРЯЪ:

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     sal = 3000

          UNION

          SELECT    ename,
                    sal,
                    job
          FROM      emp
          WHERE     job = 'clerk'
          AND       sal != 3000

хГ ЩРНЦН КЕДСЕР, ВРН МЮХАНКЕЕ БШЦНДМН ОЕПБШЛ Б WHERE ОНЛЕЫЮРЭ ОПЕДХЙЮР ЯБЪГЮММШИ Я РЕЛ СЯКНБХЕЛ, ЙНРНПНЕ БНГБПЮРХР МЮХАНКЭЬЕЕ ЙНКХВЕЯРБН ЯРПНЙ, Ю ОНЯКЕДМХЛ — ОПЕДХЙЮР БНГБПЮЫЮЧЫХИ МЮХЛЕМЭЬЕЕ ЙНКХВЕЯРБН ЯРПНЙ. рЕЛ ЯЮЛШЛ ЛШ ЛМХЛХГХПСЕЛ ЙНКХВЕЯРБН ОПНБЕПНЙ МЮ '!=' БН БРНПНЛ SELECT'Е.

нДМЮЙН, РЮЙЮЪ НОРХЛХГЮЖХЪ ГЮОПНЯНБ Я OR МЕ ЛНФЕР АШРЭ БШОНКМЕМЮ ДКЪ SQL ГЮОПНЯНБ, ЯНДЕПФЮЫХУ ОПЕДКНФЕМХЕ CONNECT BY ХКХ БМЕЬМХЕ НАЗЕДХМЕМХЪ (outer joins).

6.10 мЕ ЯННРМЕЯЕММШЕ ОНДГЮОПНЯШ

лШ ПЮЯЯЛНРПХЛ ДБЮ РХОЮ ГЮОПНЯНБ, ОЕПБШИ РХО ЩРН ГЮОПНЯШ Я НОЕПЮРНПНЛ IN, БРНПНИ РХО — Я НОЕПЮРНПНЛ NOT IN. мЮВМЕЛ Я ГЮОПНЯНБ, ЯНДЕПФЮЫХУ НОЕПЮРНП IN.

мХФЕ ОПХБЕДЕМШ ОПЮБХКЮ ОН ЙНРНПШЛ Oracle НОРХЛХГХПСЕР РЮЙХЕ ГЮОПНЯШ.

  1. нЯМНБМНИ ГЮОПНЯ Х ОНДГЮОПНЯ НОРХЛХГХПСЧРЯЪ МЕГЮБХЯХЛН ДПСЦ НР ДПСЦЮ.
  2. оПЮБХКЮ ДКЪ НОРХЛХГЮЖХХ НЯМНБМНЦН ГЮОПНЯЮ Х ОНДГЮОПНЯЮ НДХМЮЙНБШ, МЮОПХЛЕП, Б ОПХБЕДЕММШЛ МХФЕ ГЮОПНЯЕ Oracle МЕ АСДЕР НОРХЛХГХПНБЮРЭ ОНДГЮОПНЯ, РЮЙ ЙЮЙ Б МЕЛ МЕР ОПЕДКНФЕМХЪ WHERE.
  3. б ЙЮВЕЯРБЕ СОПЮБКЪЧЫЕИ РЮАКХЖШ АСДЕР БШЯРСОЮРЭ РЮАКХЖЮ ХГ ОНДГЮОПНЯЮ. б ОПХЛЕПЕ ЩРН АСДЕР РЮАКХЖЮ job.
  4. оНДГЮОПНЯ ОПЕНАПЮГСЕРЯЪ Б НАЗЕДХМЕМХЕ (join) ЯКЕДСЧЫХЛ НАПЮГНЛ. яРПНЙХ, БНГБПЮЫЮЕЛШЕ ОНДГЮОПНЯНЛ, ЯНПРХПСЧРЯЪ Х НВХЫЮЧРЯЪ НР ДСАКХЙЮРНБ, (ДКЪ ДНЯРСОЮ Й ОНКСВЕММНИ Б ПЕГСКЭРЮРЕ БШОНКМЕМХЪ ОНДГЮОПНЯЮ РЮАКХЖЕ ХЯОНКЭГСЕРЯЪ FTS), Х РЮАКХЖЮ ХГ НЯМНБМНЦН ГЮОПНЯЮ НАЗЕДХМЪЕРЯЪ (joined) Я ПЕГСКЭРЮРЮЛХ БШОНКМЕМХЪ ОНДГЮОПНЯЮ ХЯОНКЭГСЪ Б ЙЮВЕЯРБЕ ЙКЧВЮ ЙНКНМЙС, СОНЛЪМСРСЧ Б ОПЕДКНФЕМХХ WHERE Б НЯМНБМНЛ ГЮОПНЯЕ.
          SELECT    distinct name
          FROM      men
          WHERE     pin in
                    (SELECT pin
                    FROM job)

          ХМДЕЙЯШ:

ДЮЕР ЯКЕДСЧЫХИ explain plan.

          SORT(UNIQUE)
            MERGE JOIN
              TABLE ACCESS (FULL) OF 'MEN'
            SORT(JOIN)
              TABLE ACCESS (FULL) OF 'JOB'

          Execute time 4759

нОЕПЮЖХЪ SORT(UNIQUE) НАСЯКНБКЕМЮ МЮКХВХЕЛ DISTINCT Б ГЮОПНЯЕ.

еЯКХ ФЕ ЯСЫЕЯРБСЧР ХМДЕЙЯШ ЛШ ОНКСВХЛ

          SELECT    distinct name
          FROM      men
          WHERE     pin in
                    (SELECT pin
                    FROM job )

          ХМДЕЙЯШ:

          unique on job(jobno)
          non unique on job(pin)

ДЮЕР ЯКЕДСЧЫХИ explain plan.

          SORT(UNIQUE)
            NESTED LOOPS
              TABLE ACCESS (FULL) OF 'MEN'
              INDEX(RANGE SCAN) OF 'JOB_1' (NON_UNIQUE)

йЮЙ ЛШ БХДХЛ ГДЕЯЭ ХЯОНКЭГСЕРЯЪ ХМДЕЙЯ РЮАКХЖШ job. щРН РНР ПЕДЙХИ ЯКСВЮИ, ЙНЦДЮ ХМДЕЙЯШ ХЯОНКЭГСЧРЯЪ ДЮФЕ ОПХ НРЯСРЯРБХХ ОПЕДКНФЕМХЪ WHERE Б ОНДГЮОПНЯЕ.

SQL НОЕПЮРНП ЙНМЖЕОРСЮКЭМН БШОНКМЪЕРЯЪ ЙЮЙ

          SELECT distinct pin 
          FROM            job 
          ORDER BY        pin

Х ЩРХ НРЯНПРХПНБЮММШЕ ЯРПНЙХ ГЮРЕЛ НАЗЕДХМЪЧРЯЪ ЯН ЯРПНЙЮЛХ ХГ РЮАКХЖШ men Я ХЯОНКЭГНБЮМХЕЛ ХМДЕЙЯЮ ... index on job(pin).

оПХЛЕМЪРЭ НОЕПЮРНП NOT IN МЕ ПЕЙНЛЕМДСЕРЯЪ. пЮГПЮАНРВХЙЮЛ ЯКЕДСЕР ОПЕНАПЮГНБШБЮРЭ РЮЙХЕ ЙНМЯРПСЙЖХХ ХЯОНКЭГСЪ БМЕЬМХЕ НАЗЕДХМЕМХЪ (outer joins). нДМЮЙН, ЯКЕДСЕР ХЛЕРЭ ББХДС, ВРН БМЕЬМХЕ НАЗЕДХМЕМХЪ (outer joins) ЪБКЪЧРЯЪ ПЮЯЬХПЕМХЕЛ Oracle Х ЛНЦСР МЕ ОНДДЕПФХБЮРЭЯЪ Б ДПСЦХУ ясад. пЮЯЯЛНРПХЛ ЯКЕДСЧЫХИ ОПХЛЕП.

          SELECT    *
          FROM      dept
          WHERE     deptno not in
                    (SELECT   deptno
                    FROM      emp)

нМ ЛНФЕР АШРЭ ОЕПЕОХЯЮМ Я ХЯОНКЭГНБЮМХЕЛ БМЕЬМЕЦН НАЗЕДХМЕМХЪ (outer join).

          SELECT    d.*
          FROM      dept d,emp e
          WHERE     d.deptno = e.deptno(+)
          AND       e.rowid is NULL

рЮЙЮЪ МНРЮЖХЪ НЯМНБЮМЮ МЮ РНЛ, ВРН ЙЮФДЮЪ ЯРПНЙЮ ХЛЕЕР СМХЙЮКЭМШИ ROWID, ЙНРНПШИ МХЙНЦДЮ МЕ ЛНФЕР АШРЭ NULL. яКЕДСЕР НРЛЕРХРЭ РЮЙФЕ, ВРН NOT IN ЪБКЪЕРЯЪ ЩЙБХБЮКЕМРНЛ NOT EXISTS. оНЩРНЛС КЧАНИ ГЮОПНЯ Я NOT EXISTS ЛНФЕР АШРЭ ОЕПЕОХЯЮМ Я ХЯОНКЭГНБЮМХЕЛ БМЕЬМЕЦН НАЗЕДХМЕМХЪ (outer join).

6.11 яННРМЕЯЕММШЕ ОНДГЮОПНЯШ

бШОНКМЕМХЕ БЯЕУ ЯННРМЕЯЕММШУ ОНДГЮОПНЯНБ ХДЕР ОН ОНУНФЕЛС ОСРХ. нЯМНБМНИ ГЮОПНЯ Х ОНДГЮОПНЯ НОРХЛХГХПСЧРЯЪ НРДЕКЭМН. сОПЮБКЪЧЫЮЪ РЮАКХЖЮ БШАХПЮЕРЯЪ ХГ НЯМНБМНЦН ГЮОПНЯЮ. дКЪ ЙЮФДНИ ЯРПНЙХ ХГ СОПЮБКЪЧЫЕИ РЮАКХЖШ БШОНКМЪЕРЯЪ ОНДГЮОПНЯ. хМДЕЙЯШ ЛНЦСР ХЯОНКЭГНБЮРЭЯЪ Х Б НЯМНБМНЛ ГЮОПНЯЕ Х Б ОНДГЮОПНЯЕ, ЕЯКХ НМХ ЯНДЕПФЮР ОПЕДКНФЕМХЕ WHERE.

опхкнфемхе A

бЕЯНБШЕ ЙНЩТТХЖЕМРШ ОПЕДХЙЮРНБ Б ГЮОПНЯЮУ. вЕЛ МХФЕ ЙНЩТТХЖЕМР, РЕЛ БШЬЕ ЯЙНПНЯРЭ БШОНКМЕМХЪ ГЮОПНЯЮ.

  Rank     Path
  ======   ============================================
   1       ROWID = constant
   2       Unique indexed column = constant
   3       entire unique concatenated index = constant
   4       entire cluster key = corresponding
           cluster  key in another  table  in
           the same cluster
   5       entire cluster key = constant
   6       entire   non-unique   concatenated 
           index = constant
   7       non-unique single column index merge
   8       most leading concatenated index = constant
   9       indexed  column BETWEEN low value AND 
           high value, or indexed column LIKE 'C%'
           (bounded range)
  10       sort/merge (joins only)
  11       MAX or MIN of single indexed column
  12       ORDER BY entire index
  13       full table scans
  14       unindexed column = constant, or 
           column IS NULL, or  column  LIKE '%C%'
           (full table scan)

опхкнфемхе B

            яРПСЙРСПЮ РЮАКХЖ, ХЯОНКЭГСЕЛШУ Б ОПХЛЕПЮУ

table oe (id number(6,0),
          oe number(1,0),
          timestamp(date))

оНКЕ id ЯНДЕПФХР СМХЙЮКЭМШЕ ГМЮВЕМХЪ МЮВХМЮЪ Я 1.
оНКЕ oe ЯНДЕПФХР 0 ЕЯКХ id ВЕРМНЕ Х 1 ЕЯКХ id МЕВЕРМНЕ.

unique index on id
nonunique index on oe

100,000 ЯРПНЙ Б oe

table oe_link (oe   number(1),
               name char(10))

with 2 records

table oe_link_name (name char(10),
                    age  number(3))

With 1 record

people (name, sex)

job (job_id, name)

опхкнфемхе C

Update Performance                                RDBMS
John R. Pack                                    VAX/VMS
July 17, 1990                                 V6.0.30.4
(Revised 19-Sep-90)

                Using PL/SQL to Enhance
                  Update Performance

One of the slowest commands in SQL is the UPDATE. Most often, when a client complains about performance, a large, correlated update (or,worse, an uncorrelated update) is at the root of the problem.Often, even after creating the optimal indexes and fine tuning the SQL statement itself, the update is still hogging enormous CPU resources and is still the bottleneck in the user's production scheme.

The Correlated Update

This is largely due to the fact that most correlated updates require a full table scan. This results in very slow performance when the table is extremely large.

The following update statement is typical of correlated updates:

     Update Target_Table
     Set Target_Field = (Select Source_Information
                         From Source_Table
                         Where Source_Table.Key =
                         Target_Table.Key)
     Where exists (Select 'x'
                   From Source_Table
                   Where Source_Table.Key =
                   Target_Table.Key)

Performance problems arise because there is no method of eliminating rows in the Target_Table based on information in the Source_Table. If other conditions in the Update's Where clause do not disqualify most of the rows in the Target_Table, this update will require substantial processing time.

In addition, this type of query suffers because an index would not help the Target_Table access time. In fact, the only index which will improve the performance of the preceding update is an index on the Source_Table Key field. If the Source_Table is large, this is very useful.

Nevertheless, the best method of updating the table would be able to access just the correct rows in the Target_Table using an effective index. This method is now available using PL/SQL and an index on the Target_Table Key field.

The PL/SQL Update

The following PL/SQL code effectively uses an index on the Key field to access only the appropriate records in the Target_Table:

             Declare
               Cursor Source is
               Select *
               From Source_Table;
               Begin
               For Row in Source Loop
               Update Target_Table
               Set Target_Field = Row.Source_Information
               Where Key = Row.Key;
               End Loop;
               Exception
               When OTHERS Then
               Null;
             End;

This PL/SQL script loops through each of the records in the Source_Table and updates the appropriate row in the Target_Table, if any. Essentially, this transfers the full table scan to the Source_Table and allows the index on the Target_Table to be used effectively.

Performance Gain

Running a typical correlated update on an 8,000 row table to update 9 records required 19.4 CPU seconds. The same update using the PL/SQL script executed in 1.12 CPU seconds — a 94% performance improvement.

The PL/SQL script will outperform the correlated update whenever the Source_Table is smaller than the Target_Table. The larger the Target_Table compared to the Source_Table, the more substantial the performance gain. With an effective index, the size of the Target_Table is no longer a factor in the time required to update the table; the number of records being updated determines the performance.

Replacing the EXISTS subquery with IN subquery will give same improvement in most cases.

опхкнфемхе D

      GUIDELINES FOR USING THE OUTER JOIN SYNTAX




 Guidelines for Using the Outer Join Syntax       RDBMS
 RDBMS Support                                     V6.0
 October 1990

1 INTRODUCTION

The purpose of this technical note is to provide some guidelines on how to use the outer join facility provided by ORACLE.

1.1 Outer Join Semantics - Definitions

The following terms, used to describe the operation on outer joins, are defined :-

  'outer-join column' - a column reference followed  by
                        the symbol (+),  e.g.  EMPNO(+)
                        and  DEPT.DEPTNO(+)  are  outer
                        join columns

  'simple predicate'  - a logical expression containing
                        no  AND's,  OR's,  or  NOT's  (
                        usually a simple relation  such
                        as A = B )

'outer join predicate'- a  simple predicate  containing
                        one or more outer join columns.

2 OUTER JOIN SYNTAX - RULES

An outer join predicate may only contain outer join columns from one table ( in other words, all outer join columns in a single outer join predicate must belong to the same table). This means, for example, that the following statement is illegal :-

  EMP.EMPNO(+) = DEPT.DEPTNO(+)  -  outer join columns from
                                    two tables

Also, if a column in a predicate is an outer join column, then all columns from the same table must be outer join columns in that predicate. This means, for example, that the following statement is illegal :-

   EMP.SAL + EMP.COMM(+) = SALGRADE.HIGH  - mixed columns
                                            from one table

In a predicate, the table referenced with a (+) is directly 'outer joined' to all other tables in the predicate. It is indirectly 'outer joined' to any tables to which these other tables are themselves 'outer joined'. A predicate may not be directly or indirectly 'outer joined' to itself. This means, for example, that the following combination of predicates is illegal :-

        EMP.EMPNO(+)   = PERS.EMPNO
   AND  PERS.DEPTNO(+) = DEPT.DEPTNO
   AND  DEPT.JOB(+)    = EMP.JOB       - circular outer
                                         join relationship

3 OUTER JOIN EXECUTION

For a given table, T, there may be both outer join and non-outer join predicates. Execution occurs ( conceptually ) as follows :-

  1. The result of joining all tables mentioned in table T's outer join predicates is formed (by recursive application of this algorithm ).
  2. For each row of the result, a set of composite rows is formed, each consisting of the original row in the result joined to a row in table T for which the composite row satisfies all of table T's outer join predicates.
  3. If a set of composite rows is the null set, a composite row is created consisting of the original row in the result joined to a row similar to those in table T, but with all values set to null.
  4. Rows that do not pass the non-outer join predicates are removed.

This may be summarised as follows. Outer join predicates ( those with (+) after a column of table T ), are evaluated BEFORE table T is augmented with a null row. The null row is added only if there are NO rows in table T that satisfy the outer join predicates. Non-outer join predicates are evaluated AFTER table T is augmented with a null row (if needed)

4 OUTER JOIN - RECOMMENDATIONS

Certain types of outer joins in complicated logical expressions may not be well formed. In general, outer join columns in predicates that are branches of an OR should be avoided. Inconsistencies between the branches of the OR can result in an ambiguous query, and this may not be detected. It is best to confine outer join columns to the top level of the 'where' clause, or to nested AND's only.

5 OUTER JOIN - ILLUSTRATIVE EXAMPLES

5.1 Simple Outer Join

   SELECT ENAME, LOC
   FROM   DEPT, EMP
   WHERE  DEPT.DEPTNO = EMP.DEPTNO(+)

The predicate is evaluated BEFORE null augmentation. If there is a DEPT row for which there are no EMP rows, then a null EMP row is concatenated to the DEPT row.

5.2 Outer Join With Simple Post-Join Predicates

   SELECT ENAME, LOC
   FROM   DEPT, EMP
   WHERE  DEPT.DEPTNO = EMP.DEPTNO(+)
   AND    EMP.DEPTNO IS NULL

The second simple predicate is evaluated AFTER null augmentation, since there is no (+), removing rows which were not the result of null augmentation and hence leaving only DEPT rows for which there was no corresponding EMP row.

5.3 Outer Join With Additional Pre-Join Predicates

   SELECT ENAME, LOC
   FROM   DEPT, EMP
   WHERE  DEPT.DEPTNO = EMP.DEPTNO(+)
   AND    'CLERK'     = EMP.JOB(+)
   AND    EMP.DEPTNO IS NULL

The predicate on EMP.JOB is evaluated at the same time as the one on EMP.DEPTNO - before null augmentation. As a result, a null row is augmented to any DEPT row for which there are no corresponding clerks's in the EMP table. Therefore, this query displays departments containing no clerks.

Note that it the (+) were omitted from the EMP.JOB predicate, no rows would be returned. In this case, both the EMP.JOB and EMP.DEPTNO IS NULL predicates are evaluated AFTER the outer join, and there can be no rows for which both are true.

опхкнфемхе E

дЕЯЪРЭ ОПЮБХК ЯНГДЮМХЪ АШЯРПН БШОНКМЪЧЫХУЯЪ ГЮОПНЯНБ

  1. ме якедсер мевюъммн бшйкчвюрэ хяонкэгнбюмхе хмдейянб оняпедярбнл лндхтхйюжхх онкъ б опедкнфемхх WHERE.
  2. б опедкнфемхх FROM онякедмеи якедсер онлеыюрэ рюакхжс, хг йнрнпни хгбкейюеряъ мюхлемэьее йнкхвеярбн ярпнй.
  3. менаундхлн хяякеднбюрэ меяйнкэйн бюпхюмрнб мюохяюмхъ ндмнцн х рнцн фе гюопняю.
  4. якедсер хяонкэгнбюрэ оепюрнп EXISTS рюл цде щрн бнглнфмн.
  5. ме мюдн опняхрэ ъдпн ясад декюрэ анкэье, вел мсфмн.
  6. ме якедсер гюярюбкърэ ясад вюярн бшонкмърэ йнлохкъжхч гюопнянб. якедсер нрдюбюрэ опедонвремхе йнмярпсйжхх BIND.
  7. рш днкфем гмюрэ назел дюммшу х гмювемхъ онкеи х хяонкэгнбюрэ б реярюу пеюкхярхвеяйхи мюанп дюммшу.
  8. опх мюохяюмхх гюопнянб якедсер дюбюрэ яхмнмхлш рюакхжюл.
  9. ме опхлемъире ноепюрнп != еякх лнфмн нанирхяэ аег мецн.
  10. хяонкэгсире ORACLE TRACE FACILITY дкъ мюакчдемхъ гю унднл бшонкмемхъ бюьху гюопнянб

опхкнфемхе F

                         EXPLAIN Facility

MOTIVATION

There is a need for users to be able to determine the steps the system takes in performing various operations on a database. The EXPLAIN facility provides users with a convenient mechanism for getting this information. The facility stores this information in a standard database table that can be manipulated with standard SQL statements.

SYNTAX

The following syntax is based on the syntax used by DB2 for their EXPLAIN facility:

        EXPLAIN PLAN [SET STATEMENT_ID [=] ]
        [INTO ]
        FOR 

where

STATEMENT_ID
a unique optional identifier for the statement;
INTO
- allows user to save the results of the analysis in the specified table. The table must conform to the format for the table used to store the analysis ( see TABLE FORMATS section for a description of the table format ). If this clause is not specified, the system will then attempt to store the information in a table named .PLAN_TABLE . If the explicit or implicit table does not exist the EXPLAIN command will fail.
- an insert, delete, update, or query statement;

TABLE FORMATS

Core Table Format

The core table used to represent the plan information consists of the following fields:

STATEMENT_ID
- An identifier associated with the statement. If not set by the user, the identifier will be NULL. Note that a user may identify a statement by the timestamp field.
TIMESTAMP
- The date and time when the statement was analysed.
REMARKS
- Any comment the user wishes to associate with this step of the analysis.
OPERATION
- the name of the operation being performed. The following table provides a listing of the operations described by the facility.
 Operation       Description
 ---------------------------------------------------------------
 And-Equal       A retrieval utilising intersection of
                   rowids from index searches
 Connect by      A retrieval that is based on a tree walk
 Concatenation   A retrieval from a group of tables.  It is
                 essentially a UNION ALL operation of the
                 sources.  Used for OR operations.
 Counting        A node that is used to count the number of
                   rows returned from a table.  Used for queries
                   that use the ROWNUM meta-column.
 Filter          A restriction of the rows returned from a table
 First Row       A retrieval of only the first row
 For Update      A retrieval that is used for updating
 Index           A retrieval from an index
 Intersection    A retrieval of rows common to two tables
 Merge Join      A join utilising merge scans
 Minus           A retrieval of rows in Source 1 table but not in
                   Source 2 table
 Nested  Loops   A join utilising  nested  loops.  Each value 
                   in the first subnode is looked up in the 
                   second subnode.  This is often used when 
                   one table in a join is indexed and 
                   the other is not.
 Project         A retrieval of a subset of columns from a table
 Remote          A retrieval from a database other than the 
                   current database
 Sequence        An operation involving a sequence table
 Sort            A retrieval of rows ordered on some column 
                   or group of columns
 Table           A retrieval from a base table
 Union           A retrieval of unique rows from two tables
 View            A retrieval from a virtual table
 ----------------------------------------------------------------

Note that the operation shown when counting the number of rows returned by a query (i.e. select count(*)) is SORT. This is due to the way that COUNT is implemented internally. The table will not really be sorted.

OPTIONS
- an option that modifies the operation, e.g., OUTER option on join operations, rationale for sorting, type of index scan, type of filter, etc. The following table provides a list of the options for the operations that have options.
  OPERATION    OPTIONS      DESCRIPTION
  ----------------------------------------------------------
  Index        UNIQUE KEY  Unique key lookup on index
               RANGE       Index range scan
  Merge Join   OUTER       Join is an outer join
  Nested Loops OUTER       Join is an outer join
  Sort         DISTINCT    Sort is to produce distinct values
               GROUP BY    Sort is for grouping operation
               JOIN        Sort is for merge join
               ORDER BY    Sort is for order by
  Table        BY ROWID    Table scan is by rowid
               FULL        Sequential table scan
               CLUSTER     Table scan by cluster key
  -----------------------------------------------------------
OBJECT_NODE
- the name of the node that owns the database object.
OBJECT_OWNER
- the name of the schema the owns the database object.
OBJECT_NAME
- the name of the database object.
OBJECT_TYPE
- a modifier that provides descriptive information about the database object, e.g., NON-UNIQUE for indexes, etc.
OBJECT_INSTANCE
- a number corresponding to the ordinal position of the object as it appears in the original query. The numbering proceeds from left to right, outer to inner with respect to the original query text. Note that at this level, view expansion will result in rather interesting object instance numbers. We will be addressing this issue fully in future releases.
SEARCH_COLUMNS
- the number of leading columns used when searching an index.
ID
- a number assigned to this operation in the tree. Corresponds to a preorder traversal of the row source tree.
PARENT_ID
- the number assigned to the previous operation that receives information from this operation. This field combined with the ID field allows users to do a treewalk of the specified plan with the CONNECT BY statement.
POSITION
- the position this database object occupies for the previous operation.
OTHER
- other information that is specific to the row source that a user may find useful. For example, the select statement to a remote node, etc.

Sample Table Definition

create table PLAN_TABLE (
        statement_id    char(30),
        timestamp       date,
        remarks         char(80),
        operation       char(30),
        options         char(30),
        object_node     char(30),
        object_owner    char(30),
        object_name     char(30),
        object_instance numeric,
        object_type     char(30),
        search_columns  numeric,
        id              numeric,
        parent_id       numeric,
        position        numeric,
        other           long);

An SQL script to create this table resides in file xplainpl.sql in the same directory containing the file catalog.sql. This table must reside in the current schema unless you use the optional INTO clause of the EXPLAIN command.

EXAMPLES

Suppose we issue the following statements:

        EXPLAIN PLAN
        SET STATEMENT_ID = 'query1'
        INTO QUERY_PLANS
        FOR SELECT * 
            FROM  T1,T2,T3 
            WHERE T1.F1 = T2.F1 AND T2.F2 = T3.F2;

        SELECT OPERATION, OPTIONS, OBJECT_NAME, ID,
          PARENT_ID, POSITION
          FROM QUERY_PLANS
          WHERE STATEMENT_ID = 'query1'
          ORDER BY ID;

The following output would be created:

OPERATION     OPTIONS  OBJECT_NAME    ID   PARENT_ID   POSITION
---------------------------------------------------------------
MERGE JOIN                            1
MERGE JOIN                            2       1         1
SORT          JOIN                    3       2         1
TABLE ACCESS  FULL    T1              4       3         1
SORT          JOIN                    5       2         2
TABLE ACCESS  FULL    T2              6       5         1
SORT          JOIN                    7       1         1
TABLE ACCESS  FULL    T3              8       7         1

8 RECORDS selected

Suppose that an index is created on field F1 on table T1 and the following statements are issued:

        EXPLAIN PLAN
        SET STATEMENT_ID = 'query2'
        INTO QUERY_PLANS
        FOR SELECT * FROM T1 WHERE F1 > 1;


        SELECT OPERATION, OPTIONS, OBJECT_NAME, OBJECT_TYPE, 
          SEARCH_COLUMNS, ID, PREVIOUS_ID
          FROM QUERY_PLANS WHERE
          STATEMENT_ID='query2'
          ORDER BY ID;

The following output is produced:

OPERATION  OPTIONS  OBJECT_NAME OBJECT_TYPE SEARCH_COLUMNS  ID POS
-----------------------------------------------------------------
TABLE SCAN BY ROWID T1                                     1
INDEX SCAN RANGE    IT1        NON-UNIQUE     1            2    1

2 RECORDS selected

With the same conditions as before, suppose we issue the following which demonstrates an index only retrieval:

        EXPLAIN PLAN
        SET STATEMENT_ID = 'query3'
        INTO QUERY_PLANS
        FOR SELECT F1 FROM T1 WHERE F1 > 1;

        SELECT OPERATION, OPTIONS, OBJECT_NAME, OBJECT_TYPE, 
          SEARCH_COLUMNS, ID
          FROM QUERY_PLANS WHERE
          STATEMENT_ID='query3';

The following output is produced:

OPERATION   OPTIONS  OBJECT_NAME   OBJECT_TYPE  SEARCH_COLUMNS ID
------------------------------------------------------------------
INDEX SCAN   RANGE    IT1          NON-UNIQUE        1

1 RECORDS selected

The next example illustrates the output if a grouping operation is specified in the statement:

        EXPLAIN PLAN
        SET STATEMENT_ID = 'query4'
        INTO QUERY_PLANS
        FOR SELECT AVG(F1),F2 FROM T1 GROUP BY F2;

        SELECT OPERATION, OPTIONS, OBJECT_NAME, ID,
          PARENT_ID
          FROM QUERY_PLANS WHERE STATEMENT_ID = 'query4'
          ORDER BY ID;

OPERATION     OPTIONS    OBJECT_NAME       ID     PARENT_ID
-----------------------------------------------------------
SORT          GROUP BY                     1
TABLE SCAN    FULL      T1                 2        1

2 RECORDS selected

The next example illustrates the ouptut if DISTINCT is specified in the statement:

        EXPLAIN PLAN
        SET STATEMENT_ID = 'query5'
        INTO QUERY_PLANS
        FOR SELECT DISTINCT F1 FROM T1;

        SELECT OPERATION, OPTIONS, OBJECT_NAME, ID,
          PREVIOUS_ID
          FROM QUERY_PLANS WHERE STATEMENT_ID = 'query5'
          ORDER BY ID;

OPERATION     OPTIONS    OBJECT_NAME           ID   PREVIOUS_ID
--------------------------------------------------------------
SORT          DISTINCT                         1
TABLE SCAN    FULL      T1                     2         1

2 RECORDS selected

The next example illustrates the output if a subquery is specified in the statement:

        EXPLAIN PLAN
        SET STATEMENT_ID = 'query6'
        INTO QUERY_PLANS
        FOR 
             SELECT * FROM T1 
             WHERE F1 < ( SELECT F2 FROM T2 WHERE F1=3);

        SELECT OPERATION, OPTIONS, OBJECT_NAME, ID,
          PARENT_ID, POSITION
          FROM QUERY_PLANS WHERE STATEMENT_ID = 'query6'
          ORDER BY ID;


OPERATION     OPTIONS  OBJECT_NAME    ID   PARENT_ID  POSITION
--------------------------------------------------------------
FILTER          OUT                   1
TABLE SCAN      FULL  T1              2     1          1
TABLE SCAN      FULL  T2              3     1          2

3 RECORDS selected

The final example displays a complex query whose output is sent to the default plan table. ( It is assumed that this table has been created before issuing the statement.)

    EXPLAIN PLAN
    SET STATEMENT_ID = 'query7'
    FOR SELECT * FROM T1,T2 WHERE T1.F1 = T2.F1 UNION
        SELECT * FROM T2,T3 WHERE T2.F1 = T3.F1;

    SELECT OPERATION, OPTIONS, OBJECT_NAME, ID, 
           PARENT_ID, 
           POSITION
      FROM PLAN_TABLE WHERE STATEMENT_ID = 'query7'
      ORDER BY ID;

The following output is produced:

OPERATION  OPTIONS     OBJECT_NAME  ID   PARENT_ID  POSITION
------------------------------------------------------------
PROJECTION                          1
UNION                               2      1          1
SORT        DISTINCT                3      2          1
NEST LOOP                           4      3          1
TABLE SCAN  BY ROWID   T1           5      4          1
INDEX SCAN  RANGE      IT1          6      5          1
TABLE SCAN  FULL       T2           7      4          2
SORT        DISTINCT                8      2          2
MERGE JOIN                          9      8          1
SORT        JOIN                    10     9          1
TABLE SCAN  FULL       T2           11     10         1
SORT        JOIN                    12     9          2
TABLE SCAN  FULL       T3           13     12         1

13 RECORDS selected

The following example is based on the previous query. It illustrates the use of the treewalking capability in Oracle's version of SQL.

        SELECT LPAD(' ',2*LEVEL)||OPERATION, 
               OPTIONS, OBJECT_NAME
        FROM PLAN_TABLE WHERE STATEMENT_ID='query7'
        CONNECT BY PRIOR ID = PARENT_ID
           and STATEMENT_ID = 'query7'
        START WITH ID = 1
           and STATEMENT_ID = 'query7'
        ORDER BY ID;

LPAD(' ',2*LEVEL)||OPERATION    OPTIONS   OBJECT_NAME
----------------------------------------------------------
PROJECTION
  UNION
    SORT                      DISTINCT
      NEST LOOP
        TABLE SCAN            BY ROWID      T1
            INDEX SCAN        RANGE         IT1
        TABLE SCAN            FULL          T2
    SORT                      DISTINCT
      MERGE JOIN
        SORT                  JOIN
          TABLE SCAN          FULL          T2
        SORT                  JOIN
          TABLE SCAN          FULL          T3

13 RECORDS selected

HIVE: All information for read only. Please respect copyright!
Hosted by hive йца: йХЕБЯЙЮЪ ЦНПНДЯЙЮЪ АХАКХНРЕЙЮ