sql >> Database >  >> RDS >> Oracle

Dynamische PL/SQL-datumparameter met behouden tijdwaarde

Bindvariabelen gebruiken

SQL> create or replace procedure proc( p_dt in date )
  2  as
  3  begin
  4    dbms_output.put_line( to_char( p_dt, 'yyyy-mm-dd hh24:mi:ss' ));
  5  end;
  6  /

Procedure created.

SQL> declare
  2    l_sql varchar2(1000);
  3  begin
  4    l_sql := 'begin proc(:dt); end;';
  5    execute immediate l_sql using sysdate;
  6  end;
  7  /
2013-08-26 22:14:26

PL/SQL procedure successfully completed.

Het probleem met uw code is dat om uw string op te bouwen, Oracle de DATE moet converteren naar een VARCHAR2 . Het doet dat met behulp van de NLS_DATE_FORMAT . van uw sessie . Maar uw sessie is NLS_DATE_FORMAT bevat waarschijnlijk niet de tijdcomponent, dus de tijd gaat verloren wanneer uw procedure daadwerkelijk wordt aangeroepen. Het gebruik van bindvariabelen betekent dat je niet te maken krijgt met dat soort impliciete conversies (het is ook efficiënter en veiliger).

Als je echt het gebruik van bindvariabelen wilt vermijden, kun je expliciet sysdate . casten naar een string met een to_char en plaats dan een to_date in de dynamische procedureaanroep. Maar dat is veel extra code en een aantal onnodige conversies.

SQL> ed
Wrote file afiedt.buf

  1  declare
  2    l_sql varchar2(1000);
  3  begin
  4    l_sql := q'{begin proc(to_date('}' ||
  5               to_char(sysdate, 'yyyy-mm-dd hh24:mi:ss') ||
  6               q'{', 'yyyy-mm-dd hh24:mi:ss')); end;}';
  7    execute immediate l_sql;
  8* end;
SQL> /
2013-08-26 22:19:52

PL/SQL procedure successfully completed.



  1. MAX(db_timestamp) zoekopdracht vinden

  2. Relationeel databaseontwerp (MySQL)

  3. Een PHP MYSQL-rangschikkingsquery krijgen om te rangschikken op basis van de totale som van de score

  4. Waarde uit één tabelkolom halen als er twee kolommen met dezelfde naam in een sql-join bestaan