it-swarm-eu.dev

Jak k minutovému datovému typu přidám minuty?

Mám uloženou proceduru, která vloží dva záznamy do tabulky, rozdíl mezi záznamy je v tom, že časový sloupec druhého záznamu je @MinToAdd za první:

CREATE PROCEDURE CreateEntry
    /*Other columns*/
    @StartTime time(2),
    @EndTime time(2),
    @MinutesToAdd smallint
    AS
BEGIN
    SET NOCOUNT ON;

    SET @MinutesToAdd = @MinutesToAdd % 1440;   --Prevent overflow if needed?
    IF (@MinutesToAdd > 0)
    BEGIN
    INSERT INTO ClientNotification (/*Other columns*/ startTime, endTime)
        OUTPUT inserted.id
        VALUES
               (/*Other columns*/ @StartTime, @EndTime),
               (/*Other columns*/ @StartTime + @MinutesToAdd, @EndTime + @MinutesToAdd);
    END
    ELSE
    BEGIN
        /*Whatever ELSE does.*/
    END
END

Jaký je správný způsob přidání @MinutesToAdd minut do @StartTime a @EndTime?
Upozorňujeme, že používám datový typ time.

Aktualizace:
Správná odpověď by měla obsahovat následující informace:

  • Jak přidat minuty k datovému typu time.
  • To, že navrhované řešení nevede ke ztrátě přesnosti.
  • Problémy nebo obavy, které byste měli znát v případě, že by zápisy byly příliš velké na to, aby se vešly do proměnné time, nebo by mohlo dojít k převrácení proměnné time. Pokud neexistují žádné problémy, uveďte to prosím.
10
Trisped

U nových typů nemůžete použít lenivou zkratkovou aritmetiku. Snaž se:

DATEADD(MINUTE, @MinutesToAdd, @StartTime)

Všimněte si, že i když jste chránili své @MinutesToAdd před přetečením, nechránili jste výsledek před přetečením. To nevytváří chybu, ale nemusí to být výsledek, který očekáváte.

DECLARE @StartTime TIME(0) = '23:59';
DECLARE @MinutesToAdd INT = 20;

SELECT DATEADD(MINUTE, @MinutesToAdd, @StartTime);

Výsledek:

00:19:00

Předpokládám, že to musí projít nějakým druhem interní konverze, protože tento výsledek jste nemohli dosáhnout slovy:

DECLARE @StartTime TIME(0) = '24:19';

Výsledek:

Msg 241, úroveň 16, stav 1, řádek 1
Převod selhal při převodu data a/nebo času z řetězce znaků.

Musíte zvážit, jak chcete zpracovat výpočty, které vedou buď k @EndTime nebo oboje @StartTime a @EndTime být příští den.

Také - k vyřešení dalšího nového požadavku ve vaší „ideální odpovědi“ - nedochází ke ztrátě přesnosti. Podle dokumentace je návratový typ DATEADD stejný jako vstup:

Návratový datový typ je datový typ argumentu date , s výjimkou řetězcových literálů.

Proto TIME in, TIME out.

36
Aaron Bertrand

Jednoduše použijte funkci dateadd a přidejte minuty do celého čísla proti '0:00'. Pak vrhněte zpět na čas.

Vyberte cast (dateadd (minuta, 84, '0: 00') jako čas)

Zde je 84 celé číslo, které chci vyjádřit typem "time".

Přidal jsem to do '0:00' a pak abych odstranil komponentu data, vložím ji do typu času. Není třeba žádné vlastní kódování.

(Bez názvu sloupce)

01: 24: 00.0000000

0
Jun Sato