Vấn đề:
Bạn có hai cột thuộc loại datetime
và bạn muốn tính toán sự khác biệt giữa chúng.
Ví dụ:
Trong travel
bảng, có ba cột:id
, departure
và arrival
. Bạn muốn tính toán sự khác biệt giữa arrival
và departure
.
travel
bảng trông như thế này:
id | khởi hành | đến |
---|---|---|
1 | 2018-03-25 12:00:00 | 2018-04-05 07:30:00 |
2 | 2019-09-12 15:50:00 | 2019-10-23 10:30:30 |
3 | 2018-07-14 16:15:00 | 2018-07-14 20:40:30 |
4 | 2018-01-05 08:35:00 | 2019-01-08 14:00:00 |
Giải pháp 1 (chênh lệch tính bằng giây):
CHỌN id, khởi hành, đến, DATEDIFF (thứ hai, khởi hành, đến) NHƯ khác biệt FROM du lịch;
Kết quả là:
id | khởi hành | đến | sự khác biệt |
---|---|---|---|
1 | 2018-03-25 12:00:00 | 2018-04-05 07:30:00 | 934200 |
2 | 2019-09-12 15:50:00 | 2019-10-23 10:30:30 | 3523230 |
3 | 2018-07-14 16:15:00 | 2018-07-14 20:40:30 | 15930 |
4 | 2018-01-05 08:35:00 | 2019-01-08 14:00:00 | 31814700 |
Thảo luận:
Để tính toán sự khác biệt giữa arrival
và khởi hành trong T-SQL, sử dụng DATEDIFF(datepart, startdate, enddate)
hàm số. datepart
đối số có thể là microsecond
, second
, minute
, hour
, day
, week
, month
, quarter
hoặc year
. Ở đây, bạn muốn nhận được sự khác biệt trong vài giây, vì vậy hãy chọn thứ hai. Để nhận chênh lệch về giờ, hãy chọn hour
; để biết sự chênh lệch giữa các tháng, hãy chọn month
, v.v. startdate
và enddate
các đối số là datetime
bắt đầu và kết thúc các cột tương ứng (tại đây, departure
và arrival
tương ứng).
Giải pháp 2 (chênh lệch ngày, giờ, phút và giây):
WITH difference_in_seconds AS (SELECT id, khởi hành, đến, DATEDIFF (SECOND, khởi hành, đến) AS giây TỪ chuyến đi), chênh lệch AS (SELECT id, khởi hành, đến, giây, giây% 60 AS seconds_part, giây% 3600 AS phút_hạt, giây% (3600 * 24) AS giờ_part TỪ chênh lệch_in_seconds) SELECT id, khởi hành, đến, CONCAT (FLOOR (giây / 3600/24), 'ngày', FLOOR (giờ_part / 3600), 'giờ', FLOOR (phút_p) / 60), 'minutes', seconds_part, 'seconds') AS chênh lệch FROM;
Kết quả là:
id | khởi hành | đến | sự khác biệt |
---|---|---|---|
1 | 2018-03-25 12:00:00 | 2018-04-05 07:30:00 | 10 ngày 19 giờ 30 phút 0 giây |
2 | 2019-09-12 15:50:00 | 2019-10-23 10:30:30 | 40 ngày 18 giờ 40 phút 30 giây |
3 | 2018-07-14 16:15:00 | 2018-07-14 20:40:30 | 0 ngày 4 giờ 25 phút 30 giây |
4 | 2018-01-05 08:35:00 | 2019-01-08 14:00:00 | 368 ngày 5 giờ 25 phút 0 giây |
Thảo luận:
Đầu tiên, hãy tính toán sự khác biệt giữa arrival
và departure
trong vài giây, sử dụng DATEDIFF()
hàm (CTE đầu tiên, được đặt tên là difference_in_seconds
), giống như trong Giải pháp 1. Sau đó, tính xem có bao nhiêu giây vượt quá cả phút (seconds_part
) sẽ được sử dụng sau này để tính số giây, bao nhiêu giây còn lại trong tổng số giờ (minutes_part
) sẽ được sử dụng sau này để tính toán phút và số giây còn lại trong tổng số giờ (hours_part
) sẽ được sử dụng sau này để tính giờ.
Để làm điều này, hãy sử dụng toán tử%. Ví dụ:một giờ có 3600 giây, vì vậy, để tìm xem có bao nhiêu giây trong minutes_part
, hãy tìm phần còn lại của phép chia cho 3600 như sau:
seconds % 3600 AS minutes_part
Tương tự, có 3600 * 24
giây trong một ngày, vì vậy, để tính xem có bao nhiêu giây trong hours_part
, viết:
seconds % (3600 * 24) AS hours_part
Khi những phần còn lại này được tính toán (trong CTE thứ hai, được đặt tên là differences
), cuối cùng bạn có thể nhận được sự khác biệt về ngày, giờ, phút và giây. Để có số giây, phút, giờ và ngày, hãy chia số giây còn lại cho số giây tương ứng trong ngày, giờ hoặc phút. Ví dụ:để tìm ra bao nhiêu phút sẽ được hiển thị, hãy lấy minutes_part
và chia nó cho 60, vì một giờ có 60 phút. Bạn chỉ cần phần nguyên từ phần này (tức là không cần phần thập phân), vì vậy hãy sử dụng FLOOR()
chức năng như thế này:
FLOOR(minutes_part / 60)
Cuối cùng, bạn chỉ cần hiển thị trong một chuỗi những gì bạn đã tính toán. Để thực hiện việc này, hãy sử dụng CONCAT()
trong truy vấn bên ngoài:
CONCAT (FLOOR (giây / 3600/24), 'ngày', FLOOR (giờ_part / 3600), 'giờ', FLOOR (phút_hút / 60), 'phút', giây_phần, 'giây') AS chênh lệchGiải pháp được trình bày ở đây trả về một
datetime
khác biệt như một văn bản. Bạn có thể dễ dàng sửa đổi giải pháp để chỉ nhận các số mà không có bất kỳ văn bản nào. Bạn cũng có thể lưu trữ ngày, giờ, phút và giây trong các cột khác nhau:FLOOR (giây / 3600/24) AS ngày, FLOOR (giờ_part / 3600) AS giờ, FLOOR (phút_part / 60) AS phút, giây_part AS giây