J'ai du mal à piger l'effet que ça pourrait avoir sur un requête aussi simple que SELECT * FROM T.
Si on veut toutes les lignes, quelle alternative a-t-on au TABLE ACCESS FULL, dont la directive FIRST_ROWS va pouvoir tirer parti ??
Version imprimable
bon, c'est vrai que sûr une vue c'est plus clair :
Code:
1
2 SQL> create view v as select ename,dname from emp natural join dept View created.
Code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 SQL> select /*+ FIRST_ROWS(1) */ * from v ENAME DNAME ---------- -------------- SMITH RESEARCH ALLEN SALES WARD SALES JONES RESEARCH MARTIN SALES BLAKE SALES CLARK ACCOUNTING SCOTT RESEARCH KING ACCOUNTING TURNER SALES ADAMS RESEARCH JAMES SALES FORD RESEARCH MILLER ACCOUNTING
Code:
1
2
3
4
5
6
7
8 Execution Plan ---------------------------------------------------------- 0 SELECT STATEMENT Optimizer Mode=HINT: FIRST_ROWS (Cost=3 Card=1 Bytes=22) 1 0 NESTED LOOPS 2 1 NESTED LOOPS (Cost=3 Card=1 Bytes=22) 3 2 TABLE ACCESS FULL SCOTT.EMP (Cost=2 Card=1 Bytes=9) 4 2 INDEX UNIQUE SCAN SCOTT.PK_DEPT (Cost=0 Card=1) 5 1 TABLE ACCESS BY INDEX ROWID SCOTT.DEPT (Cost=1 Card=1 Bytes=13)
Code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 SQL> select /*+ ALL_ROWS */ * from v ENAME DNAME ---------- -------------- CLARK ACCOUNTING KING ACCOUNTING MILLER ACCOUNTING JONES RESEARCH FORD RESEARCH ADAMS RESEARCH SMITH RESEARCH SCOTT RESEARCH WARD SALES TURNER SALES ALLEN SALES JAMES SALES BLAKE SALES MARTIN SALES
Bon, un select * from t ne fait pas toujours un table scan, la table peut être iot, avoir des partitions, faire partie d'un cluster, et plein d'autre bizarreries.Code:
1
2
3
4
5
6
7
8 Execution Plan ---------------------------------------------------------- 0 SELECT STATEMENT Optimizer Mode=HINT: ALL_ROWS (Cost=6 Card=14 Bytes=308) 1 0 MERGE JOIN (Cost=6 Card=14 Bytes=308) 2 1 TABLE ACCESS BY INDEX ROWID SCOTT.DEPT (Cost=2 Card=4 Bytes=52) 3 2 INDEX FULL SCAN SCOTT.PK_DEPT (Cost=1 Card=4) 4 1 SORT JOIN (Cost=4 Card=14 Bytes=126) 5 4 TABLE ACCESS FULL SCOTT.EMP (Cost=3 Card=14 Bytes=126)
Oracle Corporation est en train de dire depuis quelques années que le FIRST_ROWS est maintenu uniquement pour des raisons de compatibilité (backwards compatibility). Nous ne devrions plus l'utiliser à cause des différents bugs qu'il peut générer. Jonathan Lewis a écrit plusieurs articles sur ce sujet.
Bien à vous
Mohamed Houri
peux-tu citer tes sources stpl?
C'est RULE et CHOOSE qui ne sont plus supporté, FIRST_ROWS et ALL_ROWS sont tout à fait utiles et utilisés
Voici le lien dont sur lequel je me suis appuyé
http://jonathanlewis.wordpress.com/2...ows/#more-5868
"He was using 10.2.0.3, and running with the optimizer_mode set to first_rows – which you shouldn’t really be doing with that version of Oracle since Oracle Corp. told us about 10 years ago that “first_rows is avaiable only for backwards compatibility”.
Je ne sais pas si c'est limité à la version 10.2.3 ou la remarque peut-être étendue aux versions qui ont suivi.
Bien cordialement
Mohamed Houri
tu as mal lu l'article, il parle du parametre init.ora FIRST_ROWS et non du hint FIRST_ROWS :roll:
Jonathan a écrit
ALTER SESSION SET OPTIMIZER_MODE=FIRST_ROWS_1Citation:
the optimizer doesn’t do it under first_rows optimisation. (It does if you use the slightly more appropriate first_rows(1) – the “new” improved option from 9i).
et
/*+FIRST_ROWS(1)*/
sont identiques.
Pour optimizer_mode=first_rows, en effet,
http://download.oracle.com/docs/cd/E...htm#PFGRF94566
Citation:
FIRST_ROWS
The optimizer uses a mix of cost and heuristics to find a best plan for fast delivery of the first few rows.
Note that using heuristics sometimes leads the optimizer to generate a plan with a cost that is significantly larger than the cost of a plan without applying the heuristic. FIRST_ROWS is available for backward compatibility and plan stability; use FIRST_ROWS_n instead.