DATEADD (Transact-SQL)
Возвращает дату, полученную как сумму исходной даты date и интервала number (целое число со знаком), добавленного к заданному компоненту datepart даты date.
Общие сведения обо всех типах данных и функциях даты и времени в языке Transact-SQL см. в разделе Типы данных и функции даты и времени (Transact-SQL).
Применимо для следующих объектов: SQL Server (SQL Server 2008 по текущую версию), База данных SQL Windows Azure (С первоначального выпуска по текущий выпуск). |
Cинтаксические обозначения в Transact-SQL
Синтаксис
DATEADD (datepart , number , date )
Аргументы
datepart
Компонент даты date, к которому добавляется интервал integer number. В следующей таблице перечислены все допустимые аргументы datepart. Эквивалентные переменные, определяемые пользователем, являются недопустимыми.datepart
Сокращения
year
yy, yyyy
quarter
qq, q
month
mm, m
dayofyear
dy, y
day
dd, d
week
wk, ww
weekday
dw, w
hour
hh
minute
mi, n
second
ss, s
millisecond
ms
microsecond
mcs
nanosecond
ns
number
Выражение, которое преобразуется к типу int и добавляется к компоненту datepart даты date. Допускаются пользовательские переменные.Если указать значения с десятичной дробью, дробь усекается, а не округляется.
date
Выражение, которое можно привести к значению типа time, date, smalldatetime, datetime, datetime2 или datetimeoffset. Аргумент date может быть выражением, выражением столбца, определяемой пользователем переменной или строковым литералом. Если выражение является строковым литералом, его результатом должно быть значение типа datetime. Во избежание неоднозначности используйте четырехзначную запись года. Дополнительные сведения о двузначном обозначении года см. в разделе Настройка параметра конфигурации сервера two digit year cutoff.
Типы возвращаемых данных
Тип возвращаемых данных является типом аргумента date, за исключением строковых литералов.
Тип возвращаемых данных для строкового литерала имеет тип datetime. Если строковый литерал имеет более трех позиций долей секунды (. nnn) или содержит компонент смещения часового пояса, возникнет ошибка.
Аргумент datepart
Функции dayofyear, day и weekday возвращают одинаковое значение.
Каждое выражение datepart и его краткие формы возвращают одно и то же значение.
Если datepart имеет тип month, а в месяце даты date имеется больше дней, чем в возвращаемом месяце, и день даты date не существует в этом месяце, возвращается последний день месяца. Например, в сентябре 30 дней, поэтому следующие две инструкции возвращают 2006-09-30 00:00:00.000:
SELECT DATEADD(month, 1, '2006-08-30');
SELECT DATEADD(month, 1, '2006-08-31');
Аргумент number не может выходить за диапазон типа данных int. В следующих инструкциях аргумент number превышает диапазон типа данных int на 1. Выдается следующее сообщение об ошибке: "Msg 8115, Level 16, State 2, Line 1. Arithmetic overflow error converting expression to data type int."
SELECT DATEADD(year,2147483648, '2006-07-31');
SELECT DATEADD(year,-2147483649, '2006-07-31');
Аргумент date не может быть увеличен до значения, выходящего за диапазон соответствующего типа данных. В следующих инструкциях значение number прибавляется к значению date, в результате превышается диапазон типа данных date. Выдается следующее сообщение об ошибке: "Msg 517, Level 16, State 1, Line 1 Adding a value to a 'datetime' column caused overflow."
SELECT DATEADD(year,2147483647, '2006-07-31');
SELECT DATEADD(year,-2147483647, '2006-07-31');
Значение секунд даты типа smalldatetime всегда равно 00. Если аргумент date имеет тип smalldatetime, действуют следующие условия.
Если datepart имеет значение second и number лежит между -30 и +29, добавление не выполняется.
Если datepart имеет значение second и number менее -30 или более +29, выполняется добавление времени, начиная с одной минуты.
Если datepart имеет значение millisecond и number лежит между -30001 и +29998, добавление не выполняется.
Если datepart имеет значение millisecond и number менее -30001 или более +29998, выполняется добавление времени, начиная с одной минуты.
Замечания
Функция DATEADD может использоваться в предложениях SELECT <список>, WHERE, HAVING, GROUP BY и ORDER BY.
Точность в долях секунды
Использование при сложении в качестве аргумента datepart значений microsecond или nanosecond для типов данных date: smalldatetime, date и datetime не допускается.
Миллисекунды имеют точность 3 знака (0,123), микросекунды — 6 знаков (0,123456), наносекунды — 9 знаков (0,123456789). Типы данных time, datetime2 и datetimeoffset имеют максимальную точность 7 знаков (0,1234567). Если аргументом datepart является nanosecond, аргумент number должен иметь значение 100 перед увеличением даты date на доли секунды. Значение аргумента number, находящееся в пределах 1 до 49, округляется до 0, а значение от 50 до 99 округляется до 100.
Следующие инструкции добавляют часть даты datepart: millisecond, microsecond или nanosecond.
DECLARE @datetime2 datetime2 = '2007-01-01 13:10:10.1111111';
SELECT '1 millisecond', DATEADD(millisecond,1,@datetime2)
UNION ALL
SELECT '2 milliseconds', DATEADD(millisecond,2,@datetime2)
UNION ALL
SELECT '1 microsecond', DATEADD(microsecond,1,@datetime2)
UNION ALL
SELECT '2 microseconds', DATEADD(microsecond,2,@datetime2)
UNION ALL
SELECT '49 nanoseconds', DATEADD(nanosecond,49,@datetime2)
UNION ALL
SELECT '50 nanoseconds', DATEADD(nanosecond,50,@datetime2)
UNION ALL
SELECT '150 nanoseconds', DATEADD(nanosecond,150,@datetime2);
Ниже приводится результирующий набор.
1 millisecond 2007-01-01 13:10:10.1121111
2 milliseconds 2007-01-01 13:10:10.1131111
1 microsecond 2007-01-01 13:10:10.1111121
2 microseconds 2007-01-01 13:10:10.1111131
49 nanoseconds 2007-01-01 13:10:10.1111111
50 nanoseconds 2007-01-01 13:10:10.1111112
150 nanoseconds 2007-01-01 13:10:10.1111113
Смещение часового пояса
При смещении часового пояса добавление не допускается.
Примеры
А.Увеличение части даты на интервал, равный 1
Каждая следующая инструкция увеличивает часть даты datepart на интервал, равный 1.
DECLARE @datetime2 datetime2 = '2007-01-01 13:10:10.1111111';
SELECT 'year', DATEADD(year,1,@datetime2)
UNION ALL
SELECT 'quarter',DATEADD(quarter,1,@datetime2)
UNION ALL
SELECT 'month',DATEADD(month,1,@datetime2)
UNION ALL
SELECT 'dayofyear',DATEADD(dayofyear,1,@datetime2)
UNION ALL
SELECT 'day',DATEADD(day,1,@datetime2)
UNION ALL
SELECT 'week',DATEADD(week,1,@datetime2)
UNION ALL
SELECT 'weekday',DATEADD(weekday,1,@datetime2)
UNION ALL
SELECT 'hour',DATEADD(hour,1,@datetime2)
UNION ALL
SELECT 'minute',DATEADD(minute,1,@datetime2)
UNION ALL
SELECT 'second',DATEADD(second,1,@datetime2)
UNION ALL
SELECT 'millisecond',DATEADD(millisecond,1,@datetime2)
UNION ALL
SELECT 'microsecond',DATEADD(microsecond,1,@datetime2)
UNION ALL
SELECT 'nanosecond',DATEADD(nanosecond,1,@datetime2);
Ниже приводится результирующий набор.
Year 2008-01-01 13:10:10.1111111
quarter 2007-04-01 13:10:10.1111111
month 2007-02-01 13:10:10.1111111
dayofyear 2007-01-02 13:10:10.1111111
day 2007-01-02 13:10:10.1111111
week 2007-01-08 13:10:10.1111111
weekday 2007-01-02 13:10:10.1111111
hour 2007-01-01 14:10:10.1111111
minute 2007-01-01 13:11:10.1111111
second 2007-01-01 13:10:11.1111111
millisecond 2007-01-01 13:10:10.1121111
microsecond 2007-01-01 13:10:10.1111121
nanosecond 2007-01-01 13:10:10.1111111
Б.Увеличение нескольких уровней части даты в одной инструкции
Каждая следующая инструкция увеличивает часть даты datepart на число number, достаточно большое, чтобы увеличить следующую часть даты datepart даты date.
DECLARE @datetime2 datetime2;
SET @datetime2 = '2007-01-01 01:01:01.1111111';
--Statement Result
-------------------------------------------------------------------
SELECT DATEADD(quarter,4,@datetime2); --2008-01-01 01:01:01.110
SELECT DATEADD(month,13,@datetime2); --2008-02-01 01:01:01.110
SELECT DATEADD(dayofyear,365,@datetime2); --2008-01-01 01:01:01.110
SELECT DATEADD(day,365,@datetime2); --2008-01-01 01:01:01.110
SELECT DATEADD(week,5,@datetime2); --2007-02-05 01:01:01.110
SELECT DATEADD(weekday,31,@datetime2); --2007-02-01 01:01:01.110
SELECT DATEADD(hour,23,@datetime2); --2007-01-02 00:01:01.110
SELECT DATEADD(minute,59,@datetime2); --2007-01-01 02:00:01.110
SELECT DATEADD(second,59,@datetime2); --2007-01-01 01:02:00.110
SELECT DATEADD(millisecond,1,@datetime2); --2007-01-01 01:01:01.110
В.Использование выражений в качестве аргументов number и date
В следующих примерах выражения различного типа используются в качестве аргументов для параметров number и date.
Указание столбца в качестве аргумента date
В следующем примере к каждому значению в столбце OrderDate добавляется 2 дня, чтобы получить новый столбец с именем PromisedShipDate.
USE AdventureWorks2012;
GO
SELECT SalesOrderID
,OrderDate
,DATEADD(day,2,OrderDate) AS PromisedShipDate
FROM Sales.SalesOrderHeader;
Здесь приводится частичный результирующий набор.
SalesOrderID OrderDate PromisedShipDate
------------ ----------------------- -----------------------
43659 2005-07-01 00:00:00.000 2005-07-03 00:00:00.000
43660 2005-07-01 00:00:00.000 2005-07-03 00:00:00.000
43661 2005-07-01 00:00:00.000 2005-07-03 00:00:00.000
...
43702 2005-07-02 00:00:00.000 2005-07-04 00:00:00.000
43703 2005-07-02 00:00:00.000 2005-07-04 00:00:00.000
43704 2005-07-02 00:00:00.000 2005-07-04 00:00:00.000
43705 2005-07-02 00:00:00.000 2005-07-04 00:00:00.000
43706 2005-07-03 00:00:00.000 2005-07-05 00:00:00.000
...
43711 2005-07-04 00:00:00.000 2005-07-06 00:00:00.000
43712 2005-07-04 00:00:00.000 2005-07-06 00:00:00.000
...
43740 2005-07-11 00:00:00.000 2005-07-13 00:00:00.000
43741 2005-07-12 00:00:00.000 2005-07-14 00:00:00.000
Указание пользовательских переменных в качестве аргументов number и date
В следующем примере в качестве аргументов number и date указываются пользовательские переменные.
DECLARE @days int = 365,
@datetime datetime = '2000-01-01 01:01:01.111'; /* 2000 was a leap year */;
SELECT DATEADD(day, @days, @datetime);
Ниже приводится результирующий набор.
-----------------------
2000-12-31 01:01:01.110
(1 row(s) affected)
Указание в качестве аргумента date скалярной системной функции
В следующем примере в качестве аргумента date указывается SYSDATETIME.
SELECT DATEADD(month, 1, SYSDATETIME());
Ниже приводится результирующий набор.
---------------------------
2013-02-06 14:29:59.6727944
(1 row(s) affected)
Указание в качестве аргументов number и date скалярных вложенных запросов и скалярных функций
В следующем примере скалярные вложенные запросы MAX(ModifiedDate) служат аргументами для number и date. (SELECT TOP 1 BusinessEntityID FROM Person.Person) является искусственным аргументом для числового параметра, показывающим способ выбора аргумента number из списка значений.
USE AdventureWorks2012;
GO
SELECT DATEADD(month,(SELECT TOP 1 BusinessEntityID FROM Person.Person),
(SELECT MAX(ModifiedDate) FROM Person.Person));
Указание в качестве аргументов number и date числовых выражений и скалярных системных функций
В следующем примере числовое выражение (-(10/2)), унарные операторы (-), арифметический оператор (/) и скалярные системные функции (SYSDATETIME) используются в качестве аргументов number и date.
SELECT DATEADD(month,-(10/2), SYSDATETIME());
Указание в качестве аргумента number ранжирующих функций
В следующем примере ранжирующие функции используются в качестве аргументов number.
USE AdventureWorks2012;
GO
SELECT p.FirstName, p.LastName
,DATEADD(day,ROW_NUMBER() OVER (ORDER BY
a.PostalCode),SYSDATETIME()) AS 'Row Number'
FROM Sales.SalesPerson AS s
INNER JOIN Person.Person AS p
ON s.BusinessEntityID = p.BusinessEntityID
INNER JOIN Person.Address AS a
ON a.AddressID = p.BusinessEntityID
WHERE TerritoryID IS NOT NULL
AND SalesYTD <> 0;
Указание в качестве аргумента number статистической оконной функции
В следующем примере в качестве аргумента number используется агрегатная оконная функция.
USE AdventureWorks2012;
GO
SELECT SalesOrderID, ProductID, OrderQty
,DATEADD(day,SUM(OrderQty)
OVER(PARTITION BY SalesOrderID),SYSDATETIME()) AS 'Total'
FROM Sales.SalesOrderDetail
WHERE SalesOrderID IN(43659,43664);
GO