sql >> Database teknologi >  >> RDS >> PostgreSQL

PostgreSQL datoforskel

Fejlretning

Hvad din funktion gør, kunne gøres meget enklere. Den faktiske årsag til syntaksfejlen er her:

SELECT EXTRACT(day FROM TIMESTAMP startDate - endDate) INTO diffDatePart;

Det ser ud til, at du forsøger at caste startDate til timestamp , hvilket er noget pjat til at begynde med, fordi din parameter startDate er erklæret som timestamp allerede.

Det virker heller ikke. Jeg citerer manualen her :

Det ville arbejde sådan her:

SELECT EXTRACT(day FROM startDate - endDate)::int INTO diffDatePart;

Men det ville stadig ikke give særlig mening. Du taler om "datoer", men definerer stadig dine parametre som timestamp . Du kunne rense det du har sådan her:

CREATE OR REPLACE FUNCTION f_date_diff()
  RETURNS int AS
$BODY$
DECLARE
    start_date date;
    end_date   date;
    date_diff  int;
BEGIN
SELECT evt_start_date FROM events WHERE evt_id = 5 INTO start_date;
SELECT evt_start_date FROM events WHERE evt_id = 6 INTO end_date;
date_diff := (endDate - startDate);
RETURN date_diff;
END
$BODY$ LANGUAGE plpgsql;
  • DECLARE kun nødvendigt én gang.
  • date kolonner erklæret som korrekt type date .
  • Brug ikke id'er med blandede store og små bogstaver, medmindre du ved præcis, hvad du gør.
  • Træk starten fra fra slutningen for at få et positivt tal eller anvende absolut værdioperatoren @ .
  • Siden fratrække datoer (i modsætning til at trække tidsstempler fra , som giver et interval ) giver allerede integer , forenkle til:

    SELECT (startDate - endDate) INTO diffDatePart;
    

    Eller endnu enklere som plpgsql-tildeling:

    diffDatePart := (startDate - endDate);
    

Simpel forespørgsel

Du kan løse den simple opgave med en simpel forespørgsel - ved hjælp af en underforespørgsel:

SELECT (SELECT evt_start_date
        FROM   events
        WHERE  evt_id = 6) 
      - evt_start_date AS date_diff
FROM   events
WHERE  evt_id = 5;

Eller du kan CROSS JOIN basistabellen til sig selv (1 række fra hver instans, så det er ok):

SELECT e.evt_start_date - s.evt_start_date AS date_diff
FROM   events e
      ,events s
WHERE  e.evt_id = 6
AND    s.evt_id = 5;

SQL-funktion

Hvis du insisterer på en funktion til formålet, så brug en simpel sql-funktion:

CREATE OR REPLACE FUNCTION f_date_diff(_start_id int, _end_id int)
  RETURNS int LANGUAGE sql AS
$func$
SELECT e.evt_start_date - s.evt_start_date
FROM   events s, events e
WHERE  s.evt_id = $1
AND    e.evt_id = $2
$func$;

Ring til:

SELECT  f_date_diff(5, 6);

PL/pgSQL-funktion

Hvis du insisterer på plpgsql ...

CREATE OR REPLACE FUNCTION f_date_diff(_start_id int, _end_id int)
  RETURNS int LANGUAGE plpgsql AS
$func$
BEGIN

RETURN (SELECT evt_start_date 
             - (SELECT evt_start_date FROM events WHERE evt_id = _start_id)
        FROM   events WHERE evt_id = _end_id);
END
$func$;

Samme opkald.



  1. Får du den aktuelle dato i SQL Server?

  2. Få eksekveringstid for sql-script i oracle sqlplus

  3. Tilføj sidesortering og søg ved hjælp af jquery datatable

  4. cURL og PHP viser 1