2012-07-04 34 views
8

Tôi cần thực hiện tương đối dễ giải thích nhưng (với các kỹ năng có phần hạn chế) khó có thể viết truy vấn SQL.Truy vấn SQL khó hiểu liên quan đến các giá trị liên tiếp

Giả sử chúng ta có một bảng tương tự như thế này:

exam_no | name | surname | result | date 
---------+------+---------+--------+------------ 
1  | John | Doe  | PASS | 2012-01-01 
1  | Ryan | Smith | FAIL | 2012-01-02 <-- 
1  | Ann | Evans | PASS | 2012-01-03 
1  | Mary | Lee  | FAIL | 2012-01-04 
...  | ... | ...  | ... | ... 
2  | John | Doe  | FAIL | 2012-02-01 <-- 
2  | Ryan | Smith | FAIL | 2012-02-02 
2  | Ann | Evans | FAIL | 2012-02-03 
2  | Mary | Lee  | PASS | 2012-02-04 
...  | ... | ...  | ... | ... 
3  | John | Doe  | FAIL | 2012-03-01 
3  | Ryan | Smith | FAIL | 2012-03-02 
3  | Ann | Evans | PASS | 2012-03-03 
3  | Mary | Lee  | FAIL | 2012-03-04 <-- 

Lưu ý rằng exam_nodate không nhất thiết phải liên quan như người ta có thể mong đợi từ các loại ví dụ tôi đã chọn.

Bây giờ, các truy vấn mà tôi cần làm là như sau:

  • Từ kỳ thi mới nhất (exam_no = 3) tìm thấy tất cả các sinh viên đã thất bại (John Doe, Ryan SmithMary Lee).
  • Đối với mỗi sinh viên này, hãy tìm ngày của đợt kiểm tra không thành công liên tiếp đầu tiên. Một cách khác để đặt nó là: cho mỗi học sinh này tìm thấy ngày thi đầu tiên không đạt được sau kỳ thi cuối cùng của họ. (Nhìn vào các mũi tên trong bảng).

Bảng kết quả nên được một cái gì đó như thế này:

name | surname | date_since_failing 
------+---------+-------------------- 
John | Doe  | 2012-02-01 
Ryan | Smith | 2012-01-02 
Mary | Lee  | 2012-03-04 

Làm thế nào tôi có thể thực hiện một truy vấn như vậy?

Cảm ơn bạn đã dành thời gian.

+0

Người đọc khác: lưu ý rằng anh đã gắn thẻ 'MySQL' –

+0

Giả sử bạn có thể tham gia trên cùng một bảng trên kết quả = 'FAIL' và chọn từ bảng có ngày cao nhất. Bạn đã thử cái gì? – Jocke

+0

Bạn có ý nghĩa gì với "* bài kiểm tra mới nhất *"? Bài kiểm tra có ngày mới nhất? – eggyal

Trả lời

4

Bạn có thể tận dụng thực tế là nếu ai đó vượt qua kỳ thi gần đây nhất, sau đó họ đã không thất bại bất kỳ kỳ thi kể từ khi vượt qua gần đây nhất của họ: do đó vấn đề giảm để tìm kỳ thi đầu tiên không thành công kể từ lần vượt qua gần đây nhất:

SELECT name, surname, MIN(date) date_since_fail 
FROM  results NATURAL LEFT JOIN (
    SELECT name, surname, MAX(date) lastpass 
    FROM  results 
    WHERE result = 'PASS' 
    GROUP BY name, surname 
) t 
WHERE result = 'FAIL' AND date > IFNULL(lastpass,0) 
GROUP BY name, surname 

Xem trên sqlfiddle.

+0

Đây chính xác là nó. Tôi không thể tin được nó ngắn gọn và đơn giản như thế nào. Tôi đã cố gắng thích ứng với vấn đề thực sự của mình với nỗ lực tối thiểu. Cảm ơn bạn rất nhiều. – Gabriel

0

tôi nên sử dụng một subquery đó Truy xuất cuối cùng đã thông qua kỳ thi, somthing như:

SET @query_exam_no = 3; 
SELECT 
name, 
surname, 
MIN(IF(date > last_passed_exam, date, NULL)) AS date_failing_since 
FROM 
exam_results 
LEFT JOIN (
    SELECT 
    name, 
    surname, 
    MAX(date) AS last_passed_exam 
    FROM exam_results 
    WHERE result = 'PASS' 
    GROUP BY name, surname 
) AS last_passed_exams USING (name, surname) 
HAVING 
MAX(IF(exam_no = @query_exam_no, result, NULL)) = 'FAIL' 
GROUP BY name, surname 
0

này là đủ:

select t.name, 
     t.surname, 
     t.date as 'date_since_failing' 
from tablename t 
inner join 
(
    select name, 
      surname, 
      max(exam_no) as exam_no 
    from tablename 
    group by name, surname 
    having min(result) = 'FAIL' 
) aux on t.name = aux.name and t.surname = aux.surname and t.exam_no = aux.exam_no 
0

Tình trạng bạn đang yêu cầu là tốt cho không có gì bạn có thể làm nó không có nó. Đây là ví dụ làm việc.

select 
    e.name, 
    e.sur_name, 
    min(e.date) as `LastFailed` 
from exams as e 
where e.result = 'Fail' 
group by e.name 
    order by e.name 

này tạo ra kết quả này

name   sur_name LastFailed 
Ann   Evans  2012-02-03 
John  Doe   2012-02-01 
Mary  Lee   2012-01-04 
Ryan  Smith  2012-01-02 
+0

Đây không phải là kết quả tôi đang tìm kiếm. Các ngày phải là những ngày xuất hiện trong bảng kết quả trong câu hỏi của tôi. Những gì tôi đang tìm kiếm là ngày của kỳ thi đầu tiên không thành công trong đợt kiểm tra liên tục thất bại mới nhất cho mỗi học sinh này. – Gabriel

+0

Không, xin lỗi. Kết quả tôi tìm kiếm chính xác là những gì tôi đã viết trong câu hỏi của mình.Xin vui lòng không chỉnh sửa câu hỏi của tôi để làm cho nó phù hợp với kết quả của bạn, nó thực sự thiếu tôn trọng. – Gabriel

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