0

こんにちは私はOracleで作成された次の関数を持っています。date-1およびdate-2パラメーターを関数に渡す必要があり、関数は別の日付を返す必要があります。

以下のコードを参照してください。

create or replace function GETD(p_d1   in date, 
                                p_d2   in date ) return DATE 
   as 
       l_result    DATE; 
   begin 
    SELECT EDIT_Date into l_result FROM qa.employees  WHERE qa.employee_join_date BETWEEN TO_DATE(p_d1, 'MM/DD/YYYY') AND TO_DATE(p_d2, 'MM/DD/YYYY') AND ROWNUM <= 1
    ;
       return l_result; 
  end; 

私は以下のように機能を実行します

SELECT GETD('27-JUN-12','28-JUN-12') FROM DUAL

関数がコンパイルされ、関数を実行するためのパラメーターを渡すときに、次のエラー「無効な月」が表示されます。誰かが私がどこで間違っているのか教えてもらえますか

ありがとうジャスティン

4

1 に答える 1

1

TO_DATEまず、日付変数を呼び出さないでください。NLS_DATE_FORMATこれを行う場合は、最初にセッションを使用して日付を文字列に変換し、次に指定されたフォーマットマスクを使用して文字列を日付に変換し直すようにOracleに強制します。NLS_DATE_FORMAT指定された形式マスクと一致しない場合(および、NLS_DATE_FORMATはクライアントによって制御されるため、一部のユーザーとセッションは必然的に異なる日付形式になります)、エラーが発生します。

時間コンポーネントを単に無視することを意図していると仮定すると、trunc代わりに関数を使用する必要があります。

create or replace function GETD(p_d1   in date, 
                                p_d2   in date ) 
  return DATE 
as 
  l_result    DATE; 
begin 
  SELECT EDIT_Date 
    into l_result 
    FROM qa.employees  
   WHERE qa.employee_join_date BETWEEN trunc(p_d1) AND trunc(p_d2) 
     AND ROWNUM <= 1;

  return l_result; 
end; 

条件の存在はrownum <= 1少し奇妙に思えます-employee_join_date基準に一致するテーブルから任意の行を実際にフェッチしたいということはありそうにないようです。要件がわからない場合は、最小値(または最大値)で行をフェッチする決定論的な処理を実行する必要があるようですedit_date

次に、関数を呼び出すときはDATE、文字列を渡してOracleにセッションのを使用して文字列を日付に暗黙的に変換させるのではなく、パラメータを渡す必要がありますNLS_DATE_FORMAT。日付リテラルを使用する場合

SELECT GETD(date '2012-06-27', date '2012-06-28') 
  FROM DUAL

または、を使用して文字列を日付に明示的に変換しますTO_DATE

SELECT GETD(to_date('27-JUN-12', 'DD-MON-RR'), to_date('28-JUN-12', 'DD-MON-RR')) 
  FROM DUAL

そうすれば、クライアントのに関係なく通話が機能しますNLS_DATE_FORMAT

于 2012-08-08T16:12:48.127 に答える