|
|
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Сразу оговорюсь, что речь исключительно про inner join. Нужно связать две таблицы по ключу (типу) и из полученного результата выбрать строки с определенным статусом. Какой вариант лучше? Этот: Код: plsql 1. 2. 3. 4. или этот: Код: plsql 1. 2. 3. ? На форумах встречал точку зрения, что нужно придерживаться семантики — в JOIN указывать условия для связывания и выбора данных, а в WHERE указывать условия для фильтрации данных, и с этой точки зрения первый вариант предпочтительнее и логичнее. Но на тех же форумах встречал и другую точку зрения, что WHERE применяется уже после того, как соединения и строки были выбраны, поэтому лучше использовать второй вариант. ________________________ Мы смотрим с оптимизмом... ...в оптический прицел. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 30.09.2016, 20:36 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Alibek B.Но на тех же форумах встречал и другую точку зрения, что WHERE применяется уже после того, как соединения и строки были выбраны Никогда больше не ходи на форумы, где ты увидел этот бред. Posted via ActualForum NNTP Server 1.5 ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 30.09.2016, 20:39 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Я как бы не на одном форуме это увидел. Я гуглил по запросу «oracle condition where vs join» и подобная точка зрения встречалась на разных ресурсах. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 30.09.2016, 20:55 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Alibek B.Какой вариант лучше? План смотрел? А чего тогда спрашиваешь? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 30.09.2016, 21:19 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Dimitry SibiryakovНикогда больше не ходи на форумы достаточно, чтобы он не писал на этом. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 30.09.2016, 22:40 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Alibek B.Я как бы не на одном форуме это увидел. Вот ни на один из них и не ходи. Alibek B. подобная точка зрения встречалась на разных ресурсах. Теперь у тебя есть список ресурсов, написанное на которых не стоит гроша выеденного. Posted via ActualForum NNTP Server 1.5 ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 30.09.2016, 23:44 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Alibek B.На форумах встречал точку зрения, что нужно придерживаться семантики — в JOIN указывать условия для связывания и выбора данных, а в WHERE указывать условия для фильтрации данных, и с этой точки зрения первый вариант предпочтительнее и логичнее. Вот это правильно. Alibek B.Но на тех же форумах встречал и другую точку зрения, что WHERE применяется уже после того, как соединения и строки были выбраны, поэтому лучше использовать второй вариант. А вот то или бред или ты чего-то недопонял. WHERE применяется "уже после того" при outer join а с inner join все в кучу а уж потом оптимайзер решит в каком порядке. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 00:29 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
SYА вот то или бред или ты чего-то недопонял. WHERE применяется "уже после того" при outer join... Ну как только рука поднимается такое писать? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 11:31 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
AlexFF__|SYА вот то или бред или ты чего-то недопонял. WHERE применяется "уже после того" при outer join... Ну как только рука поднимается такое писать? Для особо продвинутых: Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42. 43. 44. 45. 46. 47. 48. 49. 50. 51. 52. 53. 54. 55. 56. 57. 58. 59. 60. 61. 62. 63. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 14:49 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
И это не зависит от того ссылается ли WHERE на левую или на правую таблицу: Код: sql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. А таперичи посмотрим как Oracle расширяет оба SQL: Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42. 43. 44. 45. 46. 47. 48. 49. 50. 51. 52. 53. 54. 55. 56. 57. 58. 59. 60. 61. 62. 63. 64. 65. 66. 67. 68. 69. 70. 71. 72. 73. 74. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 15:09 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
SY, Сколько всего ненужного ты понаписал :) Достаточно только одного примера: Код: plsql 1. 2. 3. 4. Потом смотрим: SYWHERE применяется "уже после того" при outer join... Ты также продолжишь утверждать, что сначала join потом where? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 16:02 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
AlexFF__|Ты также продолжишь утверждать, что сначала join потом where? Да. Это ANSI правило. И оптимайзер руководствуясь этим решаем можно ли все до кучи или нет. Например: Код: plsql 1. 2. 3. 4. 5. Тут можно все до кучи и это видно по: Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. Оптимайзер даже поменял outer на inner join. А вот тут нельзя до кучи: Код: plsql 1. 2. 3. 4. 5. Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. Но это все об оптимайзере. А я о прогрaммисте который должен понимать что логически сначала join а уж потом filter (ибо фильтруем результат) и при outer join прописка условия в ON или в WHERE может кардинально повлиять на результат. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 17:58 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
AlexFF__|Ты также продолжишь утверждать, что сначала join потом where? Кстати, даже при native outer join Oracle делит предикаты WHERE на join conditions и filter conditions. Почитай Guidelines for Using Outer Join Syntax (Doc ID 14736.1) где четко расписан порядок действий (логический) и последним шагом является "Rows that do not pass the non-outer join predicates are removed". А non-outer join predicates и есть по сути ANSIшный WHERE ну и outer join predicates есть ANSIшный ON. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 18:52 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
SY, Если б where с предикатом по внутренней таблице применялось после, то следующий запрос валился бы с ошибкой. Код: plsql 1. 2. 3. 4. На металинке неплохое объяснение про pre/post предикаты, но там во всех предикатах фигурирует внешняя таблица. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 19:06 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
dbms_photoshopSY, Если б where с предикатом по внутренней таблице применялось после, то следующий запрос валился бы с ошибкой. Опять 25. Я говoрю про правила а ты про имплементацию. Посмотри на: Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. Ведь все расписaно - inline view делает left join a main select фильтрует результат left join'a. Ну а дальше оптимизатор колдует как эту логику оптимальней выполнить и понимает что оптимальней сначала отфильтровать левую тaблицу. Как результат, ZERODIVIDE не выскакивает. Тот-же результaт мы имеем при WHERE условие1 AND условие2 когда, например одно из них FALSE а другое вызывает ZERODIVIDE. Вот в каком порядке оптимайзер решит их выполнить зависит получим ли мы ZERODIVIDE или нет. Еще рaз, SQL стандарт четко разгранивает условия соединения и условия фильтрации и прямо говорит - сначала соединяем а потом фильтруем. A оптимизатор эти все условия рассмотрит и решит как и в каком порядке но в любом случае исходя из того что результaт должен быть такoй-же как и при сначала соединяем а потом фильтруем. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 21:56 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
SYОпять 25. Я говoрю про правила а ты про имплементацию.Когда я пытался говорить про логический порядок (правила) - набежало экспертов по имплементации. :) 16016806 SYSQL стандарт четко разгранивает условия соединения и условия фильтрации и прямо говорит - сначала соединяем а потом фильтруемБыл бы благодарен за указание где об этом сказано в стандарте SQL:2003 . Я с логической точки зрения с вами согласен, но за 20 минут найти в стандарте про порядок выполнения не удалось. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 01.10.2016, 22:52 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
dbms_photoshopБыл бы благодарен за указание где об этом сказано в стандарте Если ты ищешь что-то типа фразы "сначала join а потом where", то ничего не найдешь. Стандарт это язык определений и связей между ними. Открываем например ANSI/ISO/IEC International Standard (IS) Database Language SQL — Part 2: Foundation (SQL/Foundation) «Part 2» . Смотрим определение where clause: 7.8 <where clause> Format <where clause> ::= WHERE <search condition> Syntax Rules 1) Let T be the result of the preceding <from clause>. Each column reference directly contained in the <search condition> shall unambiguously reference a column of T or be an outer reference. Смотрим определение <from clause>: 7.5 <from clause> Format <from clause> ::= FROM <table reference list> <table reference list> ::= <table reference> [ { <comma> <table reference> }... ] Смотрим определение <table reference>: 7.6 <table reference> Function Reference a table. Format <table reference> ::= <table primary> | <joined table> Смотрим определение <joined table>: 7.7 <joined table> Function Specify a table derived from a Cartesian product, inner or outer join, or union join. Format <joined table> ::= <cross join> | <qualified join> | <natural join> | <union join> <cross join> ::= <table reference> CROSS JOIN <table primary> <qualified join> ::= <table reference> [ <join type> ] JOIN <table reference> <join specification> <natural join> ::= <table reference> NATURAL [ <join type> ] JOIN <table primary> <union join> ::= <table reference> UNION JOIN <table primary> <join specification> ::= <join condition> | <named columns join> <join condition> ::= ON <search condition> <named columns join> ::= USING <left paren> <join column list> <right paren> <join type> ::= INNER | <outer join type> [ OUTER ] <outer join type> ::= LEFT | RIGHT | FULL <join column list> ::= <column name list> То есть WHERE clause применяется к результату предшествующей FROM clause котoрая в свою очередь есть либо физическая таблица либо таблица полученная (derived) путем соединения (join) таблиц. То есть сначала join а потом WHERE. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 02.10.2016, 05:47 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
SYДа. Это ANSI правило. И оптимайзер руководствуясь этим решаем можно ли все до кучи или нет. Например: ............................................................ Но это все об оптимайзере. А я о прогрaммисте который должен понимать что логически сначала join а уж потом filter (ибо фильтруем результат) и при outer join прописка условия в ON или в WHERE может кардинально повлиять на результат. SY. Причем тут правила и примеры с expand_sql_text, показывающие запрос на входе построителя планов? Ты рассказываешь топикстартеру по сферического коня в вакууме, который будет только полезен при писании рефератов студентам. Что толку от теории логического порядка, если у ТС сейчас создается впечатление, что его предположение правильно? Alibek B.Но на тех же форумах встречал и другую точку зрения, что WHERE применяется уже после того, как соединения и строки были выбраны, поэтому лучше использовать второй вариант. Это форум oracle, тут людей интересует, как ты писал, имплементация . Так что извини, но мне кажется, что ты путаешь не только ТС, но и, учитывая твой статус, многих других интересующих. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 02.10.2016, 10:10 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Высокие материи. Влияние логического порядка на производительность, подкрепленные частными вариантами планов. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 02.10.2016, 10:14 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
SYТо есть WHERE clause применяется к результату предшествующей FROM clause В данном случае она "предшествует" чисто синтаксически. То есть выделенное предложение говорит, что WHERE в тексте запроса стоит после FROM и ничего больше. Posted via ActualForum NNTP Server 1.5 ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 02.10.2016, 11:17 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Dimitry SibiryakovSYТо есть WHERE clause применяется к результату предшествующей FROM clause В данном случае она "предшествует" чисто синтаксически. То есть выделенное предложение говорит, что WHERE в тексте запроса стоит после FROM и ничего больше. Коллеги, это уже детский сад. Соломон показал, что оно: - так работает - так реализовано - так описано в стандарте То, что в частных конкретных случаях (включая innser join) фильтры могут без нарушения логики быть протолкнуты непосредственно к rowsource - не меняет принципа. Логически предикаты where применяются к множеству, определенному from. Точка. Если начинающий программист будет воспринимать это именно так - не допустит дурацких ошибок, которыми бывает пересыпан код начинающих, не осознающих разницы. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 02.10.2016, 14:19 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
Dimitry SibiryakovSYТо есть WHERE clause применяется к результату предшествующей FROM clause В данном случае она "предшествует" чисто синтаксически. То есть выделенное предложение говорит, что WHERE в тексте запроса стоит после FROM и ничего больше. Смотрим определение where clause: 7.8 <where clause> Syntax Rules 1) Let T be the result of the preceding <from clause>. Each column reference directly contained in the <search condition> shall unambiguously reference a column of T or be an outer reference. General Rules 1) The <search condition> is applied to each row of T. The result of the <where clause> is a table of those rows of T for which the result of the <search condition> is true. То есть General Rules прямо говорит что WHERE применяется к T а T есть результат FROM а FROM есть либо таблица либо их соединение (joned table) а их соединение имеет только ON clause и никаких WHERE. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 02.10.2016, 14:20 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
andrey_anonymous... То, что в частных конкретных случаях (включая innser join) фильтры могут без нарушения логики быть протолкнуты ... не меняет принципа. ... вот это и есть главный вопрос трансформации - допустимо ли "проталкивать" t1.id <> 2, в условиях, когда внешнее соединение соединение ожидается по условию 1/(t1.id-2) > 0 Эквивалентен ли результат запроса, который должен давать ошибку на этапе построения соединения, запросу, возвращающему набор данных без ошибок. Даваемый конкретной реализацией ответ - эквивалентен, так как "проталкивание" произошло. Требуется объяснить эквивалентность без нарушения логики. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 02:47 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
AlexFF__|Это форум oracle, тут людей интересует, как ты писал, имплементация . Так что извини, но мне кажется, что ты путаешь не только ТС, но и, учитывая твой статус, многих других интересующих. Боюсь что путаешь ты сам себя. Открою тебе страшный секрет - имплементации, как таковой, нет. Есть имплементация каждой отдельно взятой версии. Сегодня так а завтра уже чуть-чуть не так. И имплементация эта нигде не документировaна и "изучаема" она чисто эмпирически. Изучать имплементацию нужно с точки зрения тюнинга но, IMHO, не более и пoсле того как четко изучил стандарт ибо не зная что должно быть на выходе невозможно оценить имплементацию. И повторюсь eсть имплементация каждой отдельно взятой версии. Поэтому перезд на новую версию всегда более или менее pain in the but. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 03:42 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
boobyвот это и есть главный вопрос трансформации - допустимо ли "проталкивать" t1.id <> 2, в условиях, когда внешнее соединение соединение ожидается по условию 1/(t1.id-2) > 0 Эквивалентен ли результат запроса, который должен давать ошибку на этапе построения соединения, запросу, возвращающему набор данных без ошибок. То есть по основному вопросу - о том, что предикаты where относятся к множеству, определенному from, возражений нет. Ок, давайте теперь рассмотрим вопрос о предикате 1/(t1.id-2) > 0. Теоретически: Предикат описывает множество, для которого указанное выражение истинно . Ничего другого он не описывает. Вопрос "истинно ли выражение 1/(t1.id-2) > 0 для t1.id = 2" определяет, входит указанная строка в множество или нет. То, что значение выражения не определено для t1.id = 2 в рамках трехзначной логики означает, что выражение не истинно и строка во множество, определенное предикатом, не входит. Таким образом, тезис, о том, что SQL-запрос "ДОЛЖЕН давать ошибку" в указанной ситуации - на самом деле ложен, выбрасывание исключения "деление на 0" следует отнести скорее к особенностям реализации , а фильтр "t1.id <> 2" можно считать (теоретически) не влияющим на результат, поскольку записи с t1.id = 2 не является элементом множества, отвечающего предикату "1/(t1.id-2) > 0". Практически: Все мы знаем, что вычисление значения выражения по сокращенному пути (short circuit evaluation) может давать тот же эффект в отношении исключительных ситуаций в императивных языках, в т.ч. в PL/SQL. И, будучи должным образом документировано, такое поведение никого это не парит. Почему подобное поведение должно беспокоить в декларативном SQL, для которого вообще не имеет смысла само понятие exception (ну нет в ЯЗЫКЕ SQL средств для работы с исключительными ситуациями)? Беспокоить может лишь нестабильность результата (то набор данных, то аварийное завершение в зависимости от положения звезд на небе) - и подобное поведение (if any) мы смело запишем в недостатки конкретной реализации. Вот как-то так. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 04:43 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
AlexFF__|Так что извини, но мне кажется, что ты путаешь не только ТС Я, как бы, живой и могу сам ответить. Я понял, что в целом всегда следует придерживаться семантики. А чтобы делать что-то нестандартно, то нужно хорошо знать, как устроено «под капотом». ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 11:14 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
andrey_anonymous... То, что значение выражения не определено для t1.id = 2 в рамках трехзначной логики означает, что выражение не истинно и строка во множество, определенное предикатом, не входит. Таким образом, тезис, о том, что SQL-запрос "ДОЛЖЕН давать ошибку" в указанной ситуации - на самом деле ложен... В целом - браво, и красиво соответствует определению операции сравнения в sql Но - andrey_anonymous... (ну нет в ЯЗЫКЕ SQL средств для работы с исключительными ситуациями)... ... это не совсем (совсем не) так. sql-99 явно определяет семантику исключительных ситуаций для вычислений. В частности, ISO/IEC 9075-2:1999 (E) 6.17 <numeric value function> <cardinality expression> ::= CARDINALITY <left paren> <collection value expression> <right paren> <absolute value expression> ::= ABS <left paren> <numeric value expression> <right paren> <modulus expression> ::= MOD <left paren> <numeric value expression dividend> <comma> <numeric value expression divisor><right paren> <numeric value expression dividend> ::= <numeric value expression> <numeric value expression divisor> ::= <numeric value expression> ... далее - ... 10) If <modulus expression> is specified, then let N be the value of the immediately contained <numeric value expression dividend> and let M be the value of the immediately contained <numeric value expression divisor>. Case: a) If either N or M is the null value, then the result is the null value. b) If M is zero, then an exception condition is raised: data exception — division by zero. c) Otherwise, the result is the unique nonnegative exact numeric value R with scale 0 (zero) such that all of the following are true: i) R has the same sign as N. ii) The absolute value of R is less than the absolute value of M. iii) N = M * K + R for some exact numeric value K with scale 0 (zero). andrey_anonymous... Беспокоить может лишь нестабильность результата (то набор данных, то аварийное завершение в зависимости от положения звезд на небе) - и подобное поведение (if any) мы смело запишем в недостатки конкретной реализации. ... ну да. Вот это - результат (состояние курсора при возникновении run-time error) как раз и оставлено на взгляд implementation. Что как-бы обессмысливает теоретическую красоту интертрепации результата логического выражения. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 11:39 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
andrey_anonymousDimitry Sibiryakovпропущено... В данном случае она "предшествует" чисто синтаксически. То есть выделенное предложение говорит, что WHERE в тексте запроса стоит после FROM и ничего больше. Коллеги, это уже детский сад. Соломон показал, что оно: - так работает - так реализовано - так описано в стандарте То, что в частных конкретных случаях (включая innser join) фильтры могут без нарушения логики быть протолкнуты непосредственно к rowsource - не меняет принципа. Логически предикаты where применяются к множеству, определенному from. Точка. Если начинающий программист будет воспринимать это именно так - не допустит дурацких ошибок, которыми бывает пересыпан код начинающих, не осознающих разницы.Все дело лишь в точности формулировок. 1. Если утверждать что where применяется после, то некоторые могут захотеть писать Код: plsql 1. 2. 3. Можно сказать, что это надо быть совсем чайником. Ну так если б ТС умел читать планы - у него и вопроса бы не возникло. 2. Формулировки, что предикаты "могут быть протолкнуты" или "оптимизатор может решить" верны в теории. На практике, предикаты по внешней таблице никогда не будут применены до, предикаты исключительно по внутренней всегда будут применены до. Полагаю тут как не играйся на двух таблицах хоть с предикатами по UDF + associate statistics + отключение всех трансформаций + что угодно - внутренний rowsource будет отфильтрован до соединения когда это возможно. 3. Ну и рассказывать про порядок применения на основании expand_sql_text и обычных (не коррелированных, не non-mergeable) inline view - это уж совсем некорректно. Тем более final query в 10053 выглядит несколько иначе. Так что просто надо разделять теорию и практику. SY, спасибо за цитату. Пропустил файл "5WD-02-Foundation-2003-09.pdf" для стандарта SQL:2003. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 11:59 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
dbms_photoshop...Все дело лишь в точности формулировок. 1. Если утверждать что where применяется после, то некоторые могут захотеть писать Код: plsql 1. 2. 3. Можно сказать, что это надо быть совсем чайником.... дело, имхо, в другом. Давайте все же внешнее соединение... Вот тут - Код: plsql 1. 2. надо полагать - чайником, т.к. из outer превратится в inner а тут? Код: plsql 1. 2. это вообще нельзя выписать без union в традиционном синтаксисе, при совершенно ясной семантике. т.е. - от перемены мест чайник кипит при разных температурах. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 12:32 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
boobydbms_photoshop...Все дело лишь в точности формулировок. 1. Если утверждать что where применяется после, то некоторые могут захотеть писать Код: plsql 1. 2. 3. Можно сказать, что это надо быть совсем чайником.... дело, имхо, в другом. Давайте все же внешнее соединение... Вот тут - Код: plsql 1. 2. надо полагать - чайником, т.к. из outer превратится в inner а тут? Код: plsql 1. 2. это вообще нельзя выписать без union в традиционном синтаксисе, при совершенно ясной семантике. т.е. - от перемены мест чайник кипит при разных температурах.Если обсуждать мышление чайников и абстрактные запросы в вакууме можно вообще далеко зайти. Так что, желательно хоть немного понимать что требуется получить. В первом случае, очевидно, отсутствие плюса в "t2.status > 0" делает этот предикат post join. Если вспользоваться case намекая на "неразрывность условий", то получим соответствующие ошибки 11g Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 12c Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. Во втором случае, если таки цель все сделать предикатами соединения (то есть догадавшись поставить (+)), получим 11g, 12c Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. или применив вышеупомянутый прием с case 11g, 12c Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 13:25 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
dbms_photoshopили применив вышеупомянутый прием с case Ну вот и expand пригодился. dbms_photoshopНу и рассказывать про порядок применения на основании expand_sql_text и обычных (не коррелированных, не non-mergeable) inline view - это уж совсем некорректно. Тем более final query в 10053 выглядит несколько иначе. Конечно иначе. Но экспанд, помимо прочего, показывает как выглядит SQL пользователя который в общем случае написан на ANSI SQL перeведенный на нативный Oracle SQL. И показывал я его только с этой точки зрения, т.е. с точки зрения логики а не имплементации - как ANSI SQL с отдельными ON и WHERE транслируется в Oracle SQL где есть тoлько WHERE при этом coблюдая логику результата. Ну а дальше, как я и говорил, колдует оптитизатор. SY. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 13:50 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
dbms_photoshop1. Если утверждать что where применяется после, то некоторые могут захотеть писать Не "после", а "к" - однако разница dbms_photoshop2. Формулировки, что предикаты "могут быть протолкнуты" или "оптимизатор может решить" верны в теории. На практике, предикаты по внешней таблице никогда не будут применены до, предикаты исключительно по внутренней всегда будут применены до. Никогда не говори "никогда": Код: plsql 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 14:50 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
dbms_photoshop, ок, за case спасибо. что касательно pre и post нет в стандарте sql ни pre ни post есть from clause, joined table, join condition есть where clause, которая по определению логически выполняется после from clause, но ни pre-condition, ни post-condition просто нет. о pre и post отдельно от join condition можно говорить только применительно к алгоритмам работы конкретного оптимизатора. Какое условие каким окажется - pre, формирующим derived table, к которой потом будет применяться join condition или уйдет на фазу post ("истинного" фильтра) - нельзя в общем предсказать даже видя конкретную запись запроса, т.к. it depends и от физики (наличия подходящих индексов, например или известных constraints) и от деталей устройства предиката и даже от фактических статистик, известных системе и оценки стоимости вычисления предиката. Для простых случаев - наверно достаточно надежно можно, в общем - нет. Так или иначе, перенос чего-то в pre или наоборот - ранний join путем слияния явно выписанной derived table - оправдывается набором трансформаций/преобразований, который оптимизатор считает допустимыми, не меняющими логически результата запроса. Все это здорово и правдоподобно, до тех пор, пока не примешивается data exception-s, которые подвешивают вопрос об эквивалентности результата. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 15:11 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
andrey_anonymousНикогда не говори "никогда"Зачет. :) Пока шел на работу и думал про прядок еще возникла мысль про экзадату, когда писал ответ - вылетело из головы. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 15:22 |
|
||
|
Где лучше указывать условие, в join или where?
|
|||
|---|---|---|---|
|
#18+
boobyок, за case спасибо.Если глянуть в final query 10053, то думаю там можно увидеть lateral и соотвественно применив lateral/outer apply получить желаемое в 12с без всяких трюков. В 11g таки необходим case. Необходимость case вообще снижается от версии к версии. То есть, подмножество запросов когда возникает ORA-01719 на 11g меньше чем на 10g, а на 12с меньше чем на 11g. И если в некоторых случаях необходимость case сомнительна, то в некоторых других - таки обязательна, иначе непонятно как трактовать одно из условий - фильтр или соединение. Я вообще написал "работу" по соединениям примерно на 20 страниц - думаю в ближайший месяц опубликую. Возможно кому-то будет полезно и/или интересно. boobyчто касательно pre и postpre и post берут свое начало из уже упомянутой ноты "Guidelines for Using Outer Join Syntax (Doc ID 14736.1)". Насколько помню первым начал применять эту терминологию на этом форуме Я и ёжик. И она имеет отношение именно к Oracle native syntax и по понятным причинам не упоминается в стандарте. Тут для полноты картины стоит отменить, что non-ANSI outer join поддерживал и MSSQL с давних времен. Только там он называется " old-style, non-SQL-92-style join " (символы =* и *=). Что еще раз подчеркивает то, что подобным образом пишут соединения не так как предписывает стандарт. Майкрософт достаточно жестко выпиливает этот синтаксис и на последних версиях он сначала выдавал предупреждение, а потом и вовсе перестал поддерживаться. Outer join operators *= and =* are not supported in 90 or later compatibility modes В других ветках форума можно найти тоже достаточно много упоминаний про pre/post join, но там они по большей части этот концепт распиарен участником Добрый Э - Эх и его клонами. :) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 03.10.2016, 15:48 |
|
||
|
|

start [/forum/topic.php?all=1&fid=52&tid=1887334]: |
0ms |
get settings: |
8ms |
get forum list: |
15ms |
check forum access: |
3ms |
check topic access: |
3ms |
track hit: |
189ms |
get topic data: |
10ms |
get forum data: |
2ms |
get page messages: |
72ms |
get tp. blocked users: |
1ms |
| others: | 198ms |
| total: | 501ms |

| 0 / 0 |
