복붙노트

[SQL] 큰 성능 차이에 의해 구별 VS기를 사용할 때

SQL

큰 성능 차이에 의해 구별 VS기를 사용할 때

나는 500 개 000 항목을 포함하는 테이블이있는 HSQLDB 서버에 대한 몇 가지 테스트를 수행하고있다. 테이블에는 인덱스가 없습니다. 5000 별개의 비즈니스 키가 있습니다. 나는 그들의 목록이 필요합니다. 당연히 나는 DISTINCT 쿼리 시작 :

SELECT DISTINCT business_key FROM memory WHERE
   concept <> 'case' or 
   attrib <> 'status' or 
   value <> 'closed'

그것은 90 초 주위에 걸립니다!

그럼 난에 의해 GROUP을 사용하여 시도 :

SELECT business_key FROM memory WHERE
       concept <> 'case' or 
       attrib <> 'status' or 
       value <> 'closed'
GROUP BY business_key

그리고 1 초 걸립니다!

내가 EXLAIN 계획을 실행 한 차이를 알아 내기 위해 노력하지만 두 쿼리에 대해 동일한 정보를 제공 할 것으로 보인다.

DISTINCT 계획을 EXPLAIN ...

isAggregated=[false]
columns=[
  COLUMN: PUBLIC.MEMORY.BUSINESS_KEY
]
[range variable 1
  join type=INNER
  table=MEMORY
  alias=M
  access=FULL SCAN
  condition = [    index=SYS_IDX_SYS_PK_10057_10058
    other condition=[
    OR arg_left=[
     OR arg_left=[
      NOT_EQUAL arg_left=[
       COLUMN: PUBLIC.MEMORY.CONCEPT] arg_right=[
       VALUE = case, TYPE = CHARACTER]] arg_right=[
      NOT_EQUAL arg_left=[
       COLUMN: PUBLIC.MEMORY.ATTRIB] arg_right=[
       VALUE = status, TYPE = CHARACTER]]] arg_right=[
     NOT_EQUAL arg_left=[
      COLUMN: PUBLIC.MEMORY.VALUE] arg_right=[
      VALUE = closed, TYPE = CHARACTER]]]
  ]
]]
PARAMETERS=[]
SUBQUERIES[]
Object References
PUBLIC.MEMORY
PUBLIC.MEMORY.CONCEPT
PUBLIC.MEMORY.ATTRIB
PUBLIC.MEMORY.VALUE
PUBLIC.MEMORY.BUSINESS_KEY
Read Locks
PUBLIC.MEMORY
WriteLocks

PLAN FOR SELECT ... GROUP BY를 EXPLAIN ...

isDistinctSelect=[false]
isGrouped=[true]
isAggregated=[false]
columns=[
  COLUMN: PUBLIC.MEMORY.BUSINESS_KEY
]
[range variable 1
  join type=INNER
  table=MEMORY
  alias=M
  access=FULL SCAN
  condition = [    index=SYS_IDX_SYS_PK_10057_10058
    other condition=[
    OR arg_left=[
     OR arg_left=[
      NOT_EQUAL arg_left=[
       COLUMN: PUBLIC.MEMORY.CONCEPT] arg_right=[
       VALUE = case, TYPE = CHARACTER]] arg_right=[
      NOT_EQUAL arg_left=[
       COLUMN: PUBLIC.MEMORY.ATTRIB] arg_right=[
       VALUE = status, TYPE = CHARACTER]]] arg_right=[
     NOT_EQUAL arg_left=[
      COLUMN: PUBLIC.MEMORY.VALUE] arg_right=[
      VALUE = closed, TYPE = CHARACTER]]]
  ]
]]
groupColumns=[
COLUMN: PUBLIC.MEMORY.BUSINESS_KEY]
PARAMETERS=[]
SUBQUERIES[]
Object References
PUBLIC.MEMORY
PUBLIC.MEMORY.CONCEPT
PUBLIC.MEMORY.ATTRIB
PUBLIC.MEMORY.VALUE
PUBLIC.MEMORY.BUSINESS_KEY
Read Locks
PUBLIC.MEMORY
WriteLocks

편집하다: 나는 추가 테스트를했다. 모두 별개의 비즈니스 키 HSQLDB 500 개 000 기록으로, DISTINCT의 성능은 이제 더 나은 - 주위 구초했다 GROUP BY 대 삼초.

MySQL의에서 두 쿼리는 동일한 수행

MySQL은 : 500 000 행 - 5 000 별개의 비즈니스 키 : 두 쿼리 : 0.5 초 MySQL은 : 500 000 행 - 모든 별개의 비즈니스 키 : 11초 - DISTINCT를 SELECT ... business_key BY SELECT ... GROUP - 13초

그래서 문제 만 HSQLDB 관련이있다.

이러한 급격한 차이가 왜 누군가가 설명 할 수 있다면 매우 감사하게 될 것입니다.

해결법

  1. ==============================

    1.두 쿼리는 같은 질문을 표현한다. 분명히 쿼리 최적화 프로그램은 두 개의 서로 다른 실행 계획을 선택합니다. 내 생각은 별개의 접근이 같이 실행되는 것입니다 :

    두 쿼리는 같은 질문을 표현한다. 분명히 쿼리 최적화 프로그램은 두 개의 서로 다른 실행 계획을 선택합니다. 내 생각은 별개의 접근이 같이 실행되는 것입니다 :

    에 의해 그룹은 같은 실행될 수 있습니다 :

    첫 번째 방법은 메모리 사용을 위해 최적화 : 임시 테이블의 일부가 스왑 아웃되어야 할 때 여전히 합리적으로 잘 수행 할 것입니다. 두 번째 방법은 속도 최적화하지만, 다른 키가 많이있는 경우 잠재적으로 많은 양의 메모리를 필요로한다.

    당신도 충분한 메모리 또는 몇 가지 다른 키를 가지고 있기 때문에, 두 번째 방법은 첫 번째를 능가하는 성능. 그것은 10 배의 성능 차이, 심지어 100 배 둘 사이의 실행 계획을보고 이상한 아니다.

  2. from https://stackoverflow.com/questions/7943957/huge-performance-difference-when-using-group-by-vs-distinct by cc-by-sa and MIT license