2012-09-17 26 views
7
+----------+--------------+-------------------------+ 
| ticketid | ticketpostid |   date   | 
+----------+--------------+-------------------------+ 
| 1387935 |  3147808 | 2012-09-17 13:33:01  | 
| 1387935 |  3147812 | 2012-09-17 13:33:41  | 
| 1387938 |  3147818 | 2012-09-17 13:35:01  | 
| 1387938 |  3148068 | 2012-09-17 13:37:01  | 
| 1387938 |  3148323 | 2012-09-17 14:47:01  | 
| 1387939 |  3147820 | 2012-09-17 13:36:01  | 
| 1387939 |  3147834 | 2012-09-17 13:36:25  | 
| 1387939 |  3147851 | 2012-09-17 13:41:01  | 
| 1387939 |  3147968 | 2012-09-17 13:59:06  | 
| 1387939 |  3147996 | 2012-09-17 14:03:01  | 

Đây là kết quả của truy vấn mà tôi đã viết. Có hai và nhiều hơn hai hàng với cùng một ticketid. Tôi cần tìm sự khác biệt về thời gian giữa hai ngày đầu tiên trong mỗi véSự khác biệt giữa các ngày trong hai hàng liên tiếp

Ví dụ:

+----------+--------------+-------------------------+ 
| ticketid | ticketpostid |   date   | 
+----------+--------------+-------------------------+ 
| 1387935 |  3147808 | 2012-09-17 13:33:01  | 
| 1387935 |  3147812 | 2012-09-17 13:33:41  | 
| 1387938 |  3147818 | 2012-09-17 13:35:01  | 
| 1387938 |  3148068 | 2012-09-17 13:37:01  | 
| 1387939 |  3147820 | 2012-09-17 13:36:01  | 
| 1387939 |  3147834 | 2012-09-17 13:36:25  | 

Kết quả là;

+----------+--------------+ 
| ticketid |time diff(sec)| 
+----------+--------------+ 
| 1387935 |  40  | 
| 1387938 |  120  | 
| 1387939 |  24  | 

Bạn có thể cho tôi biết cách tôi có thể thực hiện việc này không?

Cảm ơn.

+1

Cảm ơn các dữ liệu và kết quả mong đợi. Thật tuyệt nếu bạn thể hiện điều này trong dạng 'INSERT' để dễ tạo ra như một mẫu, nhưng nó hoạt động. BTW, phiên bản PostgreSQL nào? –

Trả lời

13

Đối với PostgreSQL, tôi nghĩ bạn muốn lag window function để so sánh các hàng; nó sẽ hiệu quả hơn nhiều so với tự kết nối và lọc. Điều này sẽ không làm việc với MySQL, vì nó vẫn không có vẻ hỗ trợ các hàm cửa sổ chuẩn SQL: 2003; xem bên dưới.

Để tìm chỉ có hai thấp nhất bạn có thể sử dụng chức năng dense_rank cửa sổ trong ticketid, sau đó lọc kết quả trở lại chỉ hàng nơi dense_rank() = 2, tức là chèo với hai từ thấp nhất timestamp, nơi lag() sẽ sản xuất hàng với dấu thời gian thấp nhất.

Xem this SQLFiddle hiển thị mẫu DDL và đầu ra.

SELECT ticketid, extract(epoch from tdiff) FROM (
    SELECT 
     ticketid, 
     ticketdate - lag(ticketdate) OVER (PARTITION BY ticketid ORDER BY ticketdate) AS tdiff, 
     dense_rank() OVER (PARTITION BY ticketid ORDER BY ticketdate) AS rank 
    FROM Table1 
    ORDER BY ticketid) x 
WHERE rank = 2; 

Tôi đã sử dụng ticketdate như tên cho cột ngày vì date là một cái tên khủng khiếp cho một cột (đó là một tên kiểu dữ liệu) và không bao giờ nên được sử dụng; nó phải được trích dẫn kép trong nhiều tình huống để làm việc.

Cách tiếp cận di động có lẽ là những người tự tham gia khác đã đăng. Cách tiếp cận hàm cửa sổ ở trên có thể hoạt động trên Oracle, nhưng dường như không có trong MySQL. Theo như tôi có thể tìm ra nó không hỗ trợ các hàm cửa sổ SQL: 2003.

Định nghĩa lược đồ sẽ hoạt động với MySQL nếu bạn SET sql_mode = 'ANSI' và sử dụng timestamp thay vì timestamp with time zone. Có vẻ như các chức năng cửa sổ sẽ không; Các cuộn cảm MySQL trên mệnh đề OVER. Xem this SQLFiddle.

1
select 
    ticketid 
    ,time_to_sec(timediff(t2.date, t1.date)) as timediff 
from table t1 
join table t2 on t1.ticketid=t2.ticketid and t1.ticketpostid<t2.ticketpostid 
+2

Tôi nghĩ rằng phương pháp này là hợp lệ, tuy nhiên, nó sẽ trả lại hàng bổ sung khi có nhiều hơn 2 của cùng một vé. Nó sẽ so sánh ticket1 với ticket2, ticket2 với ticket3, nhưng cũng ticket1 đến ticket3, điều này không được mong muốn. –

+0

Đúng, nhưng sql được thực hiện liên quan đến dữ liệu của vấn đề. Nó có thể dễ dàng sửa đổi để đưa vào xem xét 1 và 2, hoặc 1 và cuối cùng hoặc bất cứ điều gì. Nó được thực hiện cho 2 :). –

1

Hãy thử truy vấn này -

INSERT INTO ticket_post(ticketid, ticketpostid, date) VALUES 
(1387935, 3147808, '2012-09-17 13:33:01'), 
(1387935, 3147812, '2012-09-17 13:33:41'), 
(1387938, 3147818, '2012-09-17 13:35:01'), 
(1387938, 3148068, '2012-09-17 13:37:01'), 
(1387938, 3148323, '2012-09-17 14:47:01'), 
(1387939, 3147820, '2012-09-17 13:36:01'), 
(1387939, 3147834, '2012-09-17 13:36:25'), 
(1387939, 3147851, '2012-09-17 13:41:01'), 
(1387939, 3147968, '2012-09-17 13:59:06'), 
(1387939, 3147996, '2012-09-17 14:03:01'); 

SELECT 
    ticketid, 
    TIME_TO_SEC(TIMEDIFF((
    SELECT t.date FROM ticket_post t WHERE t.ticketid = t1.ticketid AND t.date > t1.date ORDER BY t.date LIMIT 1), 
    MIN(date) 
)) diff FROM ticket_post t1 
GROUP BY ticketid; 

+----------+------+ 
| ticketid | diff | 
+----------+------+ 
| 1387935 | 40 | 
| 1387938 | 120 | 
| 1387939 | 24 | 
+----------+------+ 
+0

Tôi nhận được kết quả khác nhau và tôi hơi bối rối. Bạn có thể hiển thị dữ liệu mẫu và lược đồ của mình không? So sánh: http://sqlfiddle.com/#!9/846e8/6 –

+0

Tôi đã sử dụng dữ liệu từ câu hỏi. – Devart

+0

Ah. Có hai bộ dữ liệu mẫu ở đó. Tôi đã sử dụng cái đầu, bạn dùng cái kia. Giải thích nó. Lỗi của tôi. BTW, đáng chú ý trong câu trả lời của bạn rằng nó chỉ là MySQL. –

Các vấn đề liên quan