Tôi đã tự hỏi điều tương tự. Tôi đã tìm thấy hai cách thay thế để thực hiện việc này, nhưng cách bạn đề xuất nhanh hơn.
Tôi không chính thức so sánh với một trong những bảng lớn hơn của chúng tôi. Tôi giới hạn truy vấn trong 4 triệu hàng đầu tiên. Tôi đã xen kẽ giữa hai truy vấn để tránh mang lại lợi thế không công bằng cho một truy vấn do bộ nhớ đệm db.
Trải qua thời đại kỷ nguyên / đơn nguyên
SELECT to_timestamp(
floor(EXTRACT(epoch FROM ht.time) / EXTRACT(epoch FROM interval '5 min'))
* EXTRACT(epoch FROM interval '5 min')
) FROM huge_table AS ht LIMIT 4000000
(Lưu ý rằng điều này tạo ra timestamptz
ngay cả khi bạn đã sử dụng kiểu dữ liệu không biết múi giờ)
Kết quả
- Chạy 1 :39,368 giây
- Chạy 3 :39,526 giây
- Chạy 5 :39,883 giây
Sử dụng date_trunc và date_part
SELECT
date_trunc('hour', ht.time)
+ date_part('minute', ht.time)::int / 5 * interval '5 min'
FROM huge_table AS ht LIMIT 4000000
Kết quả
- Chạy 2 :34,189 giây
- Chạy 4 :37.028 giây
- Chạy 6 :32,397 giây
Hệ thống
- Phiên bản DB:PostgreSQL 9.6.2 trên x86_64-pc-linux-gnu, được biên dịch bởi gcc (Ubuntu 4.8.2-19ubuntu1) 4.8.2, 64-bit
- Lõi:Intel® Xeon®, E5-1650v2, Hexa-Core
- RAM:64 GB, RAM DDR3 ECC
Kết luận
Phiên bản của bạn có vẻ nhanh hơn. Nhưng không đủ nhanh cho trường hợp sử dụng cụ thể của tôi. Ưu điểm của việc không phải chỉ định giờ làm cho phiên bản kỷ nguyên linh hoạt hơn và tạo ra tham số hóa đơn giản hơn trong mã phía máy khách. Nó xử lý 2 hour
khoảng thời gian cũng như 5 minute
khoảng thời gian mà không cần phải tăng date_trunc
đối số đơn vị thời gian lên. Lưu ý cuối cùng, tôi ước gì đối số đơn vị thời gian này được thay đổi thành đối số khoảng thời gian thay thế.