2013-11-15 2 views
1

아래의 Query2에서 'order by'절을 사용하면 첫 번째 결과가 즉시 반환되는 동안 1 분 이상 걸리는 이유가 무엇인지 알 수 없습니다. '에 의해 주문이 작업을 수행 할 수있는 더 나은 방법이 있나요Mysql Order By Group By By 매우 느린 쿼리

빠른 :

select c.id, max(date(a.sent)) as sent, 
    if(c.id in (select id from bin where (num=1 or num=2)),1,0) as done 
from test c, test2 a 
where c.id=a.id 
group by c.id 
limit 1; 

느린

select c.id, max(date(a.sent)) as sent, 
    if(c.id in (select id from bin where (num=1 or num=2)),1,0) as done 
from test c, test2 a 
where c.id=a.id 
group by c.id 
order by done, sent 
limit 1; 

답변

1

ORDER BY 절에서 "열"진짜 열이 없기 때문에 그것은,이다하지만 쿼리의 다른 곳에서 계산을위한 별명. 따라서 색인이 생성되지 않으며 서버는 즉시 색인을 생성해야합니다. 하위 쿼리가 아닌 완료 계산을 위해 조인을 사용하면이 작업이 훨씬 빨라질 수 있습니다.

+0

대부분의 현대 RDBMS에서 하위 쿼리는 조인보다 더 나쁩니다. 이것은 두 RDBMS가 동등한시기를 알 수없는 오래된 RDBMS에서만 발생합니다. 오늘날, 때로는 하위 쿼리가 더 좋은 방법이 될 수 있습니다 ... 모든 것이 다릅니다. –

0

모든 레코드를 다시 가져 오는 경우 정렬은 계산/인덱스되지 않은 필드 임에도 불구하고 시간이 많이 걸리지 않아야합니다. 그러나 "제한 1"을 사용하고 있습니다. 이렇게하면 옵티 마이저의 접근 방식이 변경됩니다.

첫 번째 경우 ID로 주문하고 있습니다. "제한 1"이 있고 ID에 인덱스가 있기 때문에 옵티마이 저는 ID로 ID를 처리 할 수 ​​있으며 WHERE 절과 일치하는 레코드 하나가 반환 될 때 반환 할 수 있습니다.

그러나 두 번째 쿼리에서 1 레코드 만 원한다고하더라도 옵티마이 저는 "제한 1"이없는 것처럼 전체 세트를 계산하고 반환하지 않으면 어떤 레코드인지 알 수 없습니다. 첫 번째 것만

"LIMIT 1"을 제거하고 두 쿼리를 비교하십시오. 차이가 남아있는 경우 다른 문제 일 수 있습니다.

볼륨에 가장 적합한 것이 무엇인지 말할 수 없습니다. 이 쿼리 :

select id, max(date(sent)) as sent, 0 As done 
from test2 
where exists (select 1 from bin where bin.id=test2.id and num not in (1,2)) 
group by id 
union all 
select id, max(date(sent)) as sent, 1 As done 
from test2 
where exists (select 1 from bin where bin.id=test2.id and num in (1,2)) 
group by id 
order by done, sent 
limit 1 

SQL Fiddle is here을 당신이 그것을 조정할하려는 경우.

이미 test2에있는 ID를 제외한 모든 필드를 가져 오지 않았으므로 테스트 테이블을 빠져 나갔습니다. 테스트에서 다른 필드가 필요한 경우에는이를 조정해야합니다.

+0

정확합니다. 방금 제한 1없이 두 쿼리를 실행했으며 '빠른'버전은 실제로 '빠른'버전보다 느리게 실행되었습니다. 그래서 '한계 1'이 영향을 미치고 있습니다. 예, 저는 정말로 한 레코드 만 돌려주고 싶습니다. 이 작업을 수행하는 더 좋은 방법은 무엇입니까? – user2029890

+0

감사합니다. 확실히 빠르지 만 여전히 쓸모가 없습니다. 나는 '테스트'테이블의 데이터가 필요하다. 나는 예제에 포함하지 않았다. 한 테이블에는 약 300,000 개의 레코드가 있고 다른 테이블에는 약 2 백만 개의 레코드가 있습니다. – user2029890

+0

Ok, test, test2, bin? 세 테이블 각각에 몇 개의 레코드가 있습니까? –