オプションの入力パラメータにアプローチするには、2つの可能性があります。
よりシンプル 静的SQLを使用し、デフォルトを提供する方法があります 欠落しているパラメータの値。これにより、すべての一致が得られます。
ここでは、境界を可能な最小および最大のDATEに設定するだけです。
select *
from customer
where customer_id = $P{CLIENT_ID}
and datetrx between nvl($P{DATE_START},date'1900-01-01')
and nvl($P{DATE_END},date'2200-01-01')
より高度な WayはTomKyteによって普及し、動的SQLの使用に基づいています。
パラメータが提供されている場合 、BETWEEN
を使用して通常のSQLを生成します 述語 :
select *
from customer
where customer_id = $P{CLIENT_ID}
and datetrx between $P{DATE_START} and $P{DATE_END}
パラメータが欠落している場合 (つまり、NULL
渡されます)異なるSQLを生成します 以下に示すように。
select *
from customer
where customer_id = $P{CLIENT_ID}
and (1=1 or datetrx between $P{DATE_START} and $P{DATE_END})
に注意してください
1)バインド変数の数は、クエリの両方のバリアントで同じです。これは、同じsetXXXX
を使用できるため重要です。 ステートメント
2)ショートカットによる 1 = 1 or
between
述語は無視されます。つまり、すべての日付が考慮されます。
どのオプションを使用する必要がありますか?
単純なクエリの場合はわずかな違いがありますが、パラメータが欠落していてデータが大きいといういくつかのオプションがある複雑なクエリの場合は、動的SQLアプローチが推奨されます 。
その理由は、静的SQLを使用すると、より多くの異なるクエリに同じステートメントを使用するためです。ここでは、 withにアクセスするためのステートメントです。 データ範囲とアクセス用の1つなし データ範囲。
動的オプションは、アクセスごとに異なるSQLを生成します。
実行計画に表示される場合があります:
日付範囲でのアクセス
-------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
-------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 22 | 1 (0)| 00:00:01 |
|* 1 | FILTER | | | | | |
|* 2 | INDEX RANGE SCAN| CUST_IDX1 | 1 | 22 | 1 (0)| 00:00:01 |
-------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - filter(TO_DATE(:1)<=TO_DATE(:2))
2 - access("CUSTOMER_ID"=1 AND "DATETRX">=:1 AND "DATETRX"<=:2)
データ範囲なしのアクセス
------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 22 | 1 (0)| 00:00:01 |
|* 1 | INDEX RANGE SCAN| CUST_IDX1 | 1 | 22 | 1 (0)| 00:00:01 |
------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - access("CUSTOMER_ID"=1)
どちらのステートメントも、入力パラメーター用に最適化された異なる実行プランを生成します。静的オプションでは、同じ実行プランを共有する必要があります 問題を引き起こす可能性のあるすべての入力に対して。