문제

두 개의 테이블이 있습니다.

article('id', 'ticket_id', 'incoming_time', 'to', 'from', 'message')
ticket('id', 'queue_id')

여기서 티켓은 지원 직원과 고객 사이의 이메일 스레드를 나타내고 기사는 스레드를 작성하는 개별 메시지입니다.

각 ticket_id에 대해 들어오는 시간 (UNIX 타임 스탬프로 표현 됨)이 가장 높은 기사를 찾고 있습니다. 이것은 현재 사용중인 쿼리입니다.

SELECT article.* , MAX(article.incoming_time) as maxtime
FROM ticket, article
WHERE ticket.id = article.ticket_id
AND ticket.queue_id = 1
GROUP BY article.ticket_id

예를 들어,

:article:
id --- ticket_id --- incoming_time --- to ------- from ------- message --------
11     1             1234567           help@      client@      I need help...   
12     1             1235433           client@    help@        How can we help?
13     1             1240321           help@      client@      Want food!    
...

:ticket:
id --- queue_id
1      1
...

그러나 결과는 내가 찾고있는 것 대신 가장 작은 기사 ID가있는 행으로 보입니다.

모든 조언은 대단히 감사하겠습니다!

도움이 되었습니까?

해결책

이것은 대부분의 MySQL 프로그래머가 충돌하는 고전적인 장애물입니다.

  • 열이 있습니다 ticket_id 그것이 바로 논쟁입니다 GROUP BY. 이 열의 뚜렷한 값은 그룹을 정의합니다.
  • 열이 있습니다 incoming_time 그것이 바로 논쟁입니다 MAX(). 각 그룹의 행 에서이 열에서 가장 큰 값은 다음의 값으로 리턴됩니다. MAX().
  • 다른 모든 열의 테이블 기사가 있습니다. 이 열에 대해 반환 된 값은 MAX() 값이 발생합니다.

데이터베이스는 최대 값이 발생하는 동일한 행에서 값을 원한다고 추론 할 수 없습니다.

다음 사례에 대해 생각해보십시오.

  • 동일한 최대 값이 발생하는 여러 행이 있습니다. 열을 보여주기 위해 어떤 행을 사용해야하는지 article.*?

  • 당신은 두 가지를 모두 반환하는 쿼리를 작성합니다 MIN() 그리고 MAX(). 이것은 합법적이지만 어떤 행이 있어야하는지 article.* 보여 주다?

    SELECT article.* , MIN(article.incoming_time), MAX(article.incoming_time)
    FROM ticket, article
    WHERE ticket.id = article.ticket_id
    AND ticket.queue_id = 1
    GROUP BY article.ticket_id
    
  • 다음과 같은 집계 함수를 사용합니다 AVG() 또는 SUM(), 행에 그 값이없는 경우. 데이터베이스가 어떤 행을 표시할지 추측하는 방법은 무엇입니까?

    SELECT article.* , AVG(article.incoming_time)
    FROM ticket, article
    WHERE ticket.id = article.ticket_id
    AND ticket.queue_id = 1
    GROUP BY article.ticket_id
    

대부분의 데이터베이스 브랜드와 SQL 표준 자체에서 허용되지 않습니다 모호성 때문에 이와 같은 쿼리를 작성합니다. 집계 함수 내부에 있지 않거나 GROUP BY 절.

MySQL이 더 허용됩니다. 그것은 당신이 이것을 할 수있게하고, 모호함없이 쿼리를 작성하기 위해 당신에게 맡길 수 있습니다. 모호성이있는 경우 그룹에서 물리적으로 먼저있는 행에서 값을 선택합니다 (그러나 이것은 저장 엔진에 달려 있음).

가치가있는 것에 대해 Sqlite는 또한이 행동을 가지고 있지만 마지막 모호성을 해결하기 위해 그룹에서 행을 행하십시오. 그림을 이동. SQL 표준이해야 할 일을 말하지 않으면 공급 업체 구현에 달려 있습니다.

다음은 귀하의 문제를 해결할 수있는 쿼리입니다.

SELECT a1.* , a1.incoming_time AS maxtime
FROM ticket t JOIN article a1 ON (t.id = a1.ticket_id)
LEFT OUTER JOIN article a2 ON (t.id = a2.ticket_id 
  AND a1.incoming_time < a2.incoming_time)
WHERE t.queue_id = 1
  AND a2.ticket_id IS NULL;

다시 말해, 행을 찾으십시오 (a1) 다른 행이없는 (a2) 동일하게 ticket_id 그리고 더 큰 incoming_time. 더 큰 경우 incoming_time 발견됩니다. 왼쪽 외부 결합은 일치 대신 NULL을 반환합니다.

다른 팁

SELECT a1.* FROM article a1 
JOIN 
  (SELECT MAX(a2.incoming_time) AS maxtime
   FROM article a2
   JOIN ticket ON (a2.ticketid=ticket.id)
   WHERE ticket.queue_id=1) xx
  ON (a1.incoming_time=xx.maxtime);
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top