Oracle so sánh thời gian ngày tháng

Oracle so sánh thời gian ngày tháng – Oracle compare date time

Trong quá trình sử dụng PL/SQL, ta thường xuyên phải xử lý thông tin liên quan đến thời gian ngày tháng. Một số việc liên quan đến ngày tháng trong Oracle như: insert dữ liệu vào bảng, tạo các view, cập nhật dữ liệu và tạo các báo cáo.Trong bài này tôi xin giới thiệu với các bạn một số cách trên Oracle dùng để so sánh thời gian ngày tháng.

Đối với Oracle, có kiểu dữ liệu liên quan đến ngày tháng (DateTime, Date, Timestamp) và hàm xử lý ngày tháng trong oracle (to_date(), trunc()…). Trong Oracle so sánh thời gian ngày tháng có hai cách đó là so sánh trực tiếp và gian tiếp.

So sánh thời gian ngày tháng trực tiếp

Trong Oracle, kiểu dữ liệu về thời gian ngày tháng cơ bản như dạng kiểu số nên ta có thể thao tác tính toán và so sánh như dữ liệu kiểu số (number) như bình thường. Việc so sánh này do các toán tử như lớn hơn, nhỏ hơn, bằng… giữa các dữ liệu.

Sử dụng các toán tử này có ưu điểm là không bị mất Index trên trường dữ liệu muốn so sánh nên việc so sánh thường rất là nhanh chóng và tối ưu.

Ngược lại vì kiểu ngày tháng như kiểu số nên rất chính xác nhưng kiểu ngày tháng rất phụ thuộc vào kiểu dữ liệu. Kiểu dữ liệu ngày tháng ta định nghĩa như Date, DateTime, Timestamp thường phân bậc năm – tháng – ngày – giờ – phút – giây… nên đôi lúc rất dễ nhầm lẫn khi ta so sánh mà không nắm chắc kiểu dữ liệu. Ví dụ như lấy dữ liệu của ngày hôm nay mà kiểu dữ liệu lưu là DateTime thì phải lấy dữ liệu lớn hơn hôm qua và nhỏ hơn hôm nay mới đủ. Để khắc phục điều này ta phải dùng đến hàm trunc() để làm tròn các thông tin ngày tháng để tiện so sánh và chính xác. Ta có thể tham khảo hàm trunc() với nhiều tham số như: trunc(), trunc(sysdate,’month’), trunc(sysdate, ‘year’)…

So sánh thời gian ngày tháng gián tiếp

Như đã nói ở trên, việc so sánh thời gian ngày tháng trực tiếp đôi lúc gặp một số lỗi nhất định do sơ suất. Để khắc phục điều này và làm tăng tính trực quan khi nhìn câu lệnh SQL ta có thể để Oracle so sánh thời gian một cách gián tiếp. Cũng giống như việc làm tròn dữ liệu, ta có thể chuyển đổi dữ liệu ngày tháng về cùng một định dạng khác rồi dùng chúng như một cách gián tiếp để so sánh. Ở đây tôi thường sử dụng việc chuyển đổi dữ liệu về kiểu NVARCHAR để tiến hành xử lý. Việc chuyển đổi này có nhiều điểm lợi ích ở trên nhưng có 1 nhược điểm quan trọng đó là khi sử dụng hàm to_char() để chuyển đổi ta đã vô tình làm mất Index của dữ liệu. Điều này đối với các bảng dữ liệu có lượng record lớn sẽ làm mất Index sẽ làm làm chậm hệ thống, nhưng với những lệnh SQL đơn giản thì vẫn rất thuận tiện và cần thiết. Sau đây là một số hàm so sánh bằng cách gián tiếp này:

– So sánh ngày:

Ta tiến hành convert dữ liệu dạng ngày sang kiểu string và tiến hành so sánh:

ví dụ:
Cần lấy ngày tạo lớn hơn hoặc bằng ngày 06/04/2018

AND TO_CHAR(datecreate, ‘YYYYMMDD’) >= ‘20180406’

Hoặc trong một khoảng ngày:

Cách 1:

AND TO_CHAR(datecreate, ‘YYYYMMDD’) >= ‘20180406’
AND TO_CHAR(datecreate, ‘YYYYMMDD’) < ‘20180411’

Cách 2:

AND TO_CHAR(datecreate, ‘YYYYMMDD’) between ‘20180406’ and ‘20180410’

– So sánh ngày chi tiết tới thời gian:

Ta tiến hành convert dữ liệu dạng ngày sang kiểu string và tiến hành so sánh:

ví dụ:

Cần lấy ngày tạo lớn hơn hoặc bằng 7h tối ngày 06/04/2018:

AND TO_CHAR(laa.datcre, ‘YYYYMMDD HH24:MI:SS’) >= ‘20180406 19:00:00’

Hoặc trong một khoảng thời gian:

Cách 1:

and TO_CHAR(laa.datcre, ‘YYYYMMDD HH24:MI:SS’) >= ‘20180406 19:00:00’
and TO_CHAR(laa.datcre, ‘YYYYMMDD HH24:MI:SS’) < ‘20180407 00:00:01’

Cách 2:

and TO_CHAR(laa.datcre, ‘YYYYMMDD HH24:MI:SS’) between ‘20180406 19:00:00’ and ‘20180407 00:00:00’

Có thể bạn quan tâm: