sql >> データベース >  >> RDS >> Oracle

ここで、rownum=1クエリはOracleで時間がかかります

    この質問はすでに回答済みです。フィルターROWNUM=1またはROWNUM<=1の場合に応答時間が長くなることがある理由について説明します。

    (単一のテーブルで)ROWNUMフィルターに遭遇すると、オプティマイザーはCOUNTSTOPKEYを使用してフルスキャンを生成します。これは、Oracleが最初のN行(ここではN =1)に遭遇するまで行の読み取りを開始することを意味します。フルスキャンは、最初のエクステントから最高水準点までのブロックを読み取ります。 Oracleには、どのブロックに行が含まれているか、どのブロックに含まれていないかを事前に判別する方法がないため、N行が見つかるまですべてのブロックが読み取られます。最初のブロックが空の場合、多くの読み取りが発生する可能性があります。

    次の点を考慮してください。

    SQL> /* rows will take a lot of space because of the CHAR column */
    SQL> create table example (id number, fill char(2000));
    
    Table created
    
    SQL> insert into example 
      2     select rownum, 'x' from all_objects where rownum <= 100000;
    
    100000 rows inserted
    
    SQL> commit;
    
    Commit complete
    
    SQL> delete from example where id <= 99000;
    
    99000 rows deleted
    
    SQL> set timing on
    SQL> set autotrace traceonly
    SQL> select * from example where rownum = 1;
    
    Elapsed: 00:00:05.01
    
    Execution Plan
    ----------------------------------------------------------
       0      SELECT STATEMENT Optimizer=ALL_ROWS (Cost=7 Card=1 Bytes=2015)    
       1    0   COUNT (STOPKEY)
       2    1     TABLE ACCESS (FULL) OF 'EXAMPLE' (TABLE) (Cost=7 Card=1588 [..])
    
    Statistics
    ----------------------------------------------------------
              0  recursive calls
              0  db block gets
          33211  consistent gets
          25901  physical reads
              0  redo size
           2237  bytes sent via SQL*Net to client
            278  bytes received via SQL*Net from client
              2  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
              1  rows processed
    

    ご覧のとおり、一貫した取得の数は非常に多くなっています(単一行の場合)。この状況は、たとえば、/*+APPEND*/を使用して行を挿入する場合に発生する可能性があります。 ヒント(したがって最高水準点より上)、および最も古い行も定期的に削除するため、セグメントの先頭に多くの空きスペースができます。



    1. EntityFrameworkを介してデータベースから単一の値を取得する方法

    2. MySQLデータベースの設計。 1対1のテーブルに行を挿入します。

    3. SQLクエリからカウントを取得する

    4. MySQL IN with LIKE