DBMS chính của tôi là Teradata, nhưng điều này cũng sẽ hoạt động như trong Oracle.
WITH all_meas AS (- nhận danh sách riêng biệt của tất cả các điểm từ / đến SELECT road_id, from_meas AS Measure FROM road_events UNION SELECT road_id, to_meas FROM road_events) - chọn * từ thứ tự all_meas theo 1,2, all_ranges AS (- tạo từ / đến các phạm vi CHỌN road_id, đo lường AS from_meas, Khách hàng tiềm năng (đo lường) Hơn (PARTITION BY road_id ORDER BY Measure) AS to_meas FROM all_meas) - CHỌN * từ thứ tự all_ranges 1,2, all_event_ranges AS ( - bây giờ hãy so khớp các phạm vi với các phạm vi sự kiện SELECT ar. *, re.event_id, re.year, re.total_road_length, ar.to_meas - ar.from_meas AS event_length - được sử dụng để lọc sự kiện mới nhất vì nhiều sự kiện có thể bao gồm cùng một phạm vi, Row_Number () Over (PARTITION BY ar.road_id, ar.from_meas ORDER BY year DESC) NHƯ rn FROM all_ranges ar JOIN road_events re ON ar.road_id =re.road_id VÀ ar.from_meas re.from_meas TRONG ĐÓ ar.to_meas KHÔNG ĐẦY ĐỦ) CHỌN event_id, road_id, year, total_road_length, Sum (event_length) FROM all_event_rangesWHERE rn =1 - chỉ năm mới nhấtGROUP BY event_id, road_id, year, total_road_lengthORDER BY road_id, year DESC;
Nếu bạn cần trả lại from / to_meas
được bảo hiểm thực tế (như trong câu hỏi của bạn trước khi chỉnh sửa), nó có thể phức tạp hơn. Phần đầu tiên giống nhau, nhưng không có sự tổng hợp, truy vấn có thể trả về các hàng liền kề với cùng một event_id (ví dụ:đối với sự kiện 3:0-1 &1-25):
SELECT * FROM all_event_rangesWHERE rn =1ORDER BY road_id, from_meas;
Nếu bạn muốn hợp nhất các hàng liền kề, bạn cần thêm hai bước (sử dụng cách tiếp cận tiêu chuẩn, gắn cờ cho hàng đầu tiên của một nhóm và tính toán một số nhóm):
« đo lường) Trên (PHẦN THEO ĐƠN HÀNG THEO road_id THEO số lượng) AS to_meas FROM all_meas) - CHỌN * từ thứ tự all_ranges theo 1,2, all_event_ranges AS (SELECT ar. *, re.event_id, re.year, re.total_road_length, ar. to_meas - ar.from_meas AS event_length, Row_Number () Over (PARTITION BY ar.road_id, ar.from_meas ORDER BY year DESC) AS rn FROM all_ranges ar JOIN road_events re ON ar.road_id =re.road_id AND ar.from_measChỉnh sửa:
Rất tiếc, tôi vừa tìm thấy một blog Các phạm vi chồng chéo có mức độ ưu tiên làm chính xác như vậy với một số cú pháp Oracle đơn giản hóa. Trên thực tế, tôi đã dịch truy vấn của mình từ một số cú pháp đơn giản khác trong Teradata sang Standard / Oracle SQL :-)