Ngày giờ T-SQL được làm tròn thành phút gần nhất và giờ gần nhất với việc sử dụng các hàm


113

Trong SQL server 2008, tôi muốn lấy cột ngày giờ làm tròn thành giờ gần nhất và phút gần nhất tốt nhất với các hàm hiện có trong năm 2008.

Đối với giá trị cột này 2007-09-22 15:07:38.850, kết quả sẽ giống như sau:

2007-09-22 15:08 -- nearest minute
2007-09-22 15    -- nearest hour

6
Ví dụ ở phút gần nhất không phải là 15:08? Vì giây trong một phút là 60 ...
OMG Ngựa Non

Bạn đã cố tình không sửa lỗi đó khi bạn sửa câu hỏi của anh ấy để bạn đưa ra nhận xét đó?
Mr Thứ 4, ngày

@MrWednesday Bạn nhận ra rằng có hơn 10 phút giữa chỉnh sửa và nhận xét đó. Tôi tưởng tượng ý nghĩ đó xảy ra sau đó.
lc.

Câu trả lời:


208
declare @dt datetime

set @dt = '09-22-2007 15:07:38.850'

select dateadd(mi, datediff(mi, 0, @dt), 0)
select dateadd(hour, datediff(hour, 0, @dt), 0)

sẽ trở lại

2007-09-22 15:07:00.000
2007-09-22 15:00:00.000

Phần trên chỉ cắt bớt giây và phút, tạo ra kết quả được yêu cầu trong câu hỏi. Như @OMG Ponies đã chỉ ra, nếu bạn muốn làm tròn lên / xuống, thì bạn có thể thêm nửa phút hoặc nửa giờ tương ứng, sau đó cắt bớt:

select dateadd(mi, datediff(mi, 0, dateadd(s, 30, @dt)), 0)
select dateadd(hour, datediff(hour, 0, dateadd(mi, 30, @dt)), 0)

và bạn sẽ nhận được:

2007-09-22 15:08:00.000
2007-09-22 15:00:00.000

Trước khi kiểu dữ liệu ngày tháng được thêm vào SQL Server 2008, tôi sẽ sử dụng phương pháp trên để cắt bớt phần thời gian khỏi ngày giờ để chỉ lấy ngày. Ý tưởng là xác định số ngày giữa ngày giờ được đề cập và một thời điểm cố định ( 0, ngầm hiểu là 1900-01-01 00:00:00.000):

declare @days int
set @days = datediff(day, 0, @dt)

và sau đó cộng số ngày đó vào thời điểm cố định, cung cấp cho bạn ngày ban đầu với thời gian được đặt thành 00:00:00.000:

select dateadd(day, @days, 0)

hoặc ngắn gọn hơn:

select dateadd(day, datediff(day, 0, @dt), 0)

Sử dụng một datepart khác nhau (ví dụ hour, mi) sẽ làm việc cho phù hợp.


2
Tôi nghi ngờ bất kỳ ai khác sẽ gặp phải điều này, nhưng nếu bạn đang cố gắng làm tròn LÊN đến giây gần nhất và thêm 500 mili giây thì bạn sẽ muốn thực hiện dateiff (giây, '1/1/2000', .... so với dateiff (giây, 0 .... vì bạn sẽ gặp lỗi tràn. Tôi đoán số giây từ 0 là quá lớn.
Eric Twilegar 24/02/16

'Thêm số giờ kể từ ngày 1 tháng 1 năm 1900 đến ngày 1 tháng 1 năm 1900' - Tôi gặp điều này trong Java / SQL, nơi nó trông xấu xí. Trong trường hợp của tôi, nó thực sự nên được thực hiện ở phía Java.
Corwin Newall

Đối với các phép tính với datetimeoffset, tôi phải thay thế 0bằng TODATETIMEOFFSET('1900-01-01 00:00:00', 0)để tránh ép múi giờ địa phương vào kết quả.
krlmlr

26

"Làm tròn" xuống như trong ví dụ của bạn. Điều này sẽ trả về một giá trị varchar của ngày.

DECLARE @date As DateTime2
SET @date = '2007-09-22 15:07:38.850'

SELECT CONVERT(VARCHAR(16), @date, 120) --2007-09-22 15:07
SELECT CONVERT(VARCHAR(13), @date, 120) --2007-09-22 15

Chuyển đổi varchar trở lại datetime có thể làm (đối với giờ):CONVERT(datetime, CONVERT(VARCHAR(13), @date, 120)+':00:00')
Decula

10

Tôi nhận ra câu hỏi này là cổ xưa và có một câu trả lời được chấp nhận và một câu trả lời thay thế. Tôi cũng nhận ra rằng câu trả lời của tôi sẽ chỉ trả lời một nửa câu hỏi, nhưng đối với bất kỳ ai muốn làm tròn đến phút gần nhất và vẫn có giá trị tương thích với datetime chỉ bằng một hàm duy nhất :

CAST(YourValueHere as smalldatetime);

Trong nhiều giờ hoặc vài giây, hãy sử dụng câu trả lời của Jeff Ogata (câu trả lời được chấp nhận) ở trên.


1
Câu trả lời tuyệt vời, tôi đã xác minh rằng nó làm tròn và không chỉ cắt ngắn. Đối với bất kỳ ai khác đang tìm kiếm tùy chọn này, smalldatetimeđã được thêm vào SQL 2008.
BradC 12/04/19

Đây là tùy chọn tốt nhất nếu bạn đang cần sửa một số dữ liệu trong bảng của mình mà chỉ yêu cầu hết thời gian đến từng phút.
Mã hóa

-1

Select convert(char(8), DATEADD(MINUTE, DATEDIFF(MINUTE, 0, getdate), 0), 108) as Time

sẽ làm tròn giây xuống 00


Rất chậm, và không tròn trịa như OP yêu cầu, mà làm tròn lại, điều mà anh ta không hỏi. (Tuyên bố từ chối trách nhiệm - Tôi đã không bỏ phiếu cho bạn)
Kỹ sư đảo ngược
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.