Oracle、SQL * NetまたはORDER BYはネットワークリソースを節約します...

ORDER BY構文は結果のソートにリソースを費やすと誰もが正しく信じており、最終的には少し後で結果を取得する必要があります。 これは常にそうですか?..



簡単な些細なクエリを紹介しましょう:



SET echo OFF SET linesize 192 SET pagesize 0 SET TRIM ON SET trims ON SET feedback OFF SET heading OFF SET term OFF SET TIME ON SET timing ON SET autot ON stat spool s.txt SELECT clnt_clnt_id, name, start_date, end_date FROM client_histories; spool OFF exit
      
      







すべてがシンプルなようです:

  1. テーブルから選択が行われます
  2. 結果はファイルに駆動されます
  3. 結果は端末に表示されません
  4. リクエストの最後に、時間と統計が表示されます




次に、統計を見てみましょう。



 .: 00:00:17.97  ---------------------------------------------------------- 0 recursive calls 0 db block gets 6515 consistent gets 0 physical reads 0 redo size 14182576 bytes sent via SQL*Net to client 242558 bytes received via SQL*Net from client 22012 SQL*Net roundtrips to/from client 0 sorts (memory) 0 sorts (disk) 330154 rows processed
      
      







ここで、データを合理化する必要があると想像してください。 質問-時間とともにどうなりますか? 最初の意見は、ソートには時間がかかり、結果は後から来るということです。 よくやった:



 SET echo OFF SET linesize 192 SET pagesize 0 SET TRIM ON SET trims ON SET feedback OFF SET heading OFF SET term OFF SET time ON SET timing ON SET autot ON stat spool s1.txt SELECT clnt_clnt_id , name , start_date , end_date FROM client_histories ORDER BY 1, 2; spool OFF exit
      
      







次に、統計を見てみましょう。



 .: 00:00:16.92  ---------------------------------------------------------- 0 recursive calls 0 db block gets 6115 consistent gets 0 physical reads 0 redo size 13166047 bytes sent via SQL*Net to client 242558 bytes received via SQL*Net from client 22012 SQL*Net roundtrips to/from client 1 sorts (memory) 0 sorts (disk) 330154 rows processed
      
      







order byを使用した場合、結果がより速く得られることがわかりました。 統計では、操作に費やされる時間とSQL * Netを介して送信される情報量の2つの違いのみがあります。



結論の1つは、既存のチャネルで992 kbのデータを送信するよりも、ソート操作が33,000行速いことです。



しかし、違いはどこから来たのですか?..

そして、事はsql * netを介して送信されたデータはバッファによって圧縮され、圧縮されるということです。 これは、TNS SQL * Net記述のSDUサイズと、デフォルトで15であるARRAYSIZEパラメーターを使用してSQL * Plusで構成されたバッファーのサイズの影響を受けます。データがソートされている場合、バッファーのデータは同じになり、圧縮率は高くなります。 T.O. SQL * Netを介して転送されるデータは少なくなります。



実験してみましょう。つまり、2番目のスクリプトに小さな変更を加えます。



 SET autot ON stat SET arraysize 5000 spool s1.txt
      
      







これで、バッファーのサイズを5000(これが最大値)に増やし、ソートを使用してリクエストを実行しました。 結果を見てみましょう:



 .: 00:00:06.47  ---------------------------------------------------------- 0 recursive calls 0 db block gets 6115 consistent gets 0 physical reads 0 redo size 11278863 bytes sent via SQL*Net to client 1174 bytes received via SQL*Net from client 68 SQL*Net roundtrips to/from client 1 sorts (memory) 0 sorts (disk) 330154 rows processed
      
      











合計:バッファの増加により、データ転送中のラウンドトリップの回数が減ります。これは、ほとんどの場合、大きなリクエストに対してプラスの効果をもたらします。 しかし、興味深いことに、低速の通信チャネル(たとえば、1 m /ビット以下)では、通常のデータの並べ替えでさえ、リクエスト配信の結果にプラスの影響を与える可能性があります。



はい、圧縮の観点から。 次のようにデータを準備します。



 CREATE TABLE tbl0 AS SELECT object_name, object_id, min(object_id) over (partition BY object_name) AS min_object_id FROM dba_objects; CREATE TABLE tbl1 AS SELECT DISTINCT object_name, object_id FROM tbl0 WHERE object_id = min_object_id; CREATE TABLE tbl2 AS SELECT object_name FROM tbl1 WHERE rownum < 1; BEGIN FOR i IN 1..20 LOOP INSERT INTO tbl2 SELECT object_name FROM tbl1 ORDER BY reverse(object_id||object_name); END LOOP; COMMIT; END;
      
      







ここで、ARRAYSIZE 5000の統計とクエリを比較します。



 SELECT object_name FROM tbl2; SELECT object_name FROM tbl2 ORDER BY 1;
      
      







次の統計を取得します。



  ---------------------------------------------------------- 0 recursive calls 0 db block gets 4992 consistent gets 0 physical reads 0 redo size 34152895 bytes sent via SQL*Net to client 3088 bytes received via SQL*Net from client 250 SQL*Net roundtrips to/from client 0 sorts (memory) 0 sorts (disk) 1242280 rows processed  ---------------------------------------------------------- 167 recursive calls 16 db block gets 5211 consistent gets 16377 physical reads 0 redo size 7629058 bytes sent via SQL*Net to client 3088 bytes received via SQL*Net from client 250 SQL*Net roundtrips to/from client 21 sorts (memory) 4 sorts (disk) 1242280 rows processed
      
      







ご覧のように、ARRAYSIZE 5000を使用すると、同じ数の往復で120万行すべてがポンピングされます。 SQLの影響*リクエスト/レスポンスに対するネット遅延はほぼ同じですが、ソートされたデータの情報量は、ソートされていないデータの32.5 mbに対して7.3 mbです。 T.O. 繰り返しデータの予備ソートでは、ネットワーク上のトラフィック量を4.5倍削減しました。これは、低速の通信チャネルでは非常に重要です。




All Articles