简体   繁体   中英

SQL Server - Week Ending

I have the following T-SQL code that works but I think may be reduced but not sure how.

SELECT 
    datepart(YEAR, CONVERT(DATE, GETDATE())) AS 'Year', 
    Cast(Datepart(month, DATEADD (D, -1 * DatePart (DW, getdate()) + 7, getdate())) AS VARCHAR) + '-' + Cast(Datepart(DAY, DATEADD (D, -1 * DatePart (DW, getdate()) + 7, getdate()))AS VARCHAR) [Week Ending]

I just want to get the week ending in a format with the year in another column so I can group it by year and then week ending. Can some help out.

Couldn't you do this?:

DATEADD(DAY, 7 - DATEPART(WEEKDAY, GETDATE()), CAST(GETDATE() AS DATE)) [WeekEnd]

No reason to necessarily to separate out the year in a separate column.

EDIT: I'm not sure what you mean by your comment. This prints out dates, and in date format rather than varchar - not week numbers are your comment suggests.

examples:

DECLARE @dateTime datetime
SET     @dateTime = '2016-01-01'
select  DATEADD(DAY, 7 - DATEPART(WEEKDAY, @dateTime), CAST(@dateTime AS DATE)) [WeekEnd]

2016-01-02

DECLARE @dateTime datetime
SET     @dateTime = '2016-01-04'
select  DATEADD(DAY, 7 - DATEPART(WEEKDAY, @dateTime), CAST(@dateTime AS DATE)) [WeekEnd]

2016-01-09

Sample of use:

DECLARE @table TABLE (orderDate datetime, orderAmount float)
INSERT INTO @table
(
    orderDate,
    orderAmount
)
SELECT '2015-01-02', 500
union all SELECT '2015-01-04', 500
union all SELECT '2015-01-05', 500
union all SELECT '2015-01-05', 500
union all SELECT '2015-01-06', 500
union ALL SELECT '2015-01-11', 400
union all SELECT '2016-01-01', 500
union all SELECT '2016-01-02', 500
union all SELECT '2016-01-04', 500
union all SELECT '2016-01-05', 500
union all SELECT '2016-01-05', 500
union all SELECT '2016-01-06', 500
UNION ALL SELECT '2016-01-11', 400
UNION ALL SELECT '2016-12-11', 1200

Order amount per date:

SELECT  
    orderDate, 
    sum(orderAmount) AS orderSumForGrouping, 
    count(1) AS numberOfOrdersWithinGrouping
FROM    @table o
GROUP   BY orderDate

Output:

orderDate   orderSumForGrouping numberOfOrdersWithinGrouping
2015-01-02 00:00:00.000 500 1
2015-01-04 00:00:00.000 500 1
2015-01-05 00:00:00.000 1000    2
2015-01-06 00:00:00.000 500 1
2015-01-11 00:00:00.000 400 1
2016-01-01 00:00:00.000 500 1
2016-01-02 00:00:00.000 500 1
2016-01-04 00:00:00.000 500 1
2016-01-05 00:00:00.000 1000    2
2016-01-06 00:00:00.000 500 1
2016-01-11 00:00:00.000 400 1
2016-12-11 00:00:00.000 1200    1

Order amounts grouped by year:

SELECT  
    year(orderDate) AS orderYear, 
    sum(orderAmount) AS orderSumForGrouping, 
    count(1) AS numberOfOrdersWithinGrouping
FROM    @table o
GROUP   BY year(orderDate)

Output:

orderYear   orderSumForGrouping numberOfOrdersWithinGrouping
2015    2900    6
2016    4600    8

Order amounts grouped by week-end date:

SELECT  
    DATEADD(DAY, 7 - DATEPART(WEEKDAY, orderDate), CAST(orderDate AS DATE)) AS ordersPerWeek, 
    sum(orderAmount) AS orderSumForGrouping, 
    count(1) AS numberOfOrdersWithinGrouping
FROM    @table o
GROUP   BY DATEADD(DAY, 7 - DATEPART(WEEKDAY, orderDate), CAST(orderDate AS DATE))

Output:

ordersPerWeek   orderSumForGrouping numberOfOrdersWithinGrouping
2015-01-03  500 1
2015-01-10  2000    4
2015-01-17  400 1
2016-01-02  1000    2
2016-01-09  2000    4
2016-01-16  400 1
2016-12-17  1200    1

observe that 2016-01-02 , 2016-01-09 , and 2016-01-16 are all Saturdays - the last day of the week. (holds true for the other dates as well, but these dates just occurred so are easiest to check)

One way I could make it a little smaller is by creating an auto computed column for WeekEnd and reuse it in the query:

Setup:

-- drop table testTable
create table testTable
(
    MyDate SMALLDATETIME,
    WeekEnd AS DATEADD (D, -1 * DatePart(DW, MyDate) + 7, MyDate)
)
GO

INSERT INTO testTable VALUES ('20141201'), ('20150101'), ('20150130')
GO

select * from testTable
GO

Query:

select CAST(Datepart(month, WeekEnd) AS VARCHAR) + ' - ' + CAST(Datepart(day, WeekEnd) AS VARCHAR) AS [Week Ending]
from testTable

Unfortunately, I could not make the column persisted (I cannot convince SQL Server that what I am doing is deterministic, even if using a function with schema binding). This would be great, as persisted computed columns can be indexed.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM