DB/SQL

MYSQL 실행계획 EXPLAIN

호두밥 2021. 10. 8. 10:04

EXPLAIN 실행계획 출력 항목

항목 설명
ID The SELECT identifier
SELECT 문 실행 순서
SELECT_TYPE The SELECT type
SELECT 유형
TABLE The table for the output row
PARTITIONS The matching partitions
테이블 파티션을 나타내는 정보로, NULL이면 파티션 테이블이 아님.
TYPE The join type
테이블의 데이터를 어떻게 찾을지에 대한 정보, 테이블 전체를 탐색하는지, 인덱스를 이용해 탐색하는 지에 대한 정보를 알 수 있음.
POSSIBLE_KEYS The possible indexes to choose
사용할 수 있는 인덱스 후보군
KEY The index actually chosen
실제 사용한 PK나 인덱스
KEY_LEN The length of the chosen key
사용한 인덱스의 바이트 수
REF The columns compared to the index
조인 수행 시에 사용된 칼럼(조인 조건)
ROWS Estimate of rows to be examined
SQL문 수행시 접근하는 모든 데이터 ROWS 수
FILTERED Percentage of rows filtered by table condition
접근한 데이터 전체에서 조건에 의해 출력된 데이터의 비율
EXTRA Additional information

 

SELECT 유형 / SELECT_TYPE

SELECT 문이 단순한 SELECT문인지, 서브쿼리인지, UNION으로 묶인 것인지를 알려주는 정보. 

SELECT_TYPE 설명
SIMPLE Simple SELECT (not using UNION or subqueries)
PRIMARY Outermost SELECT
서브쿼리가 있을 때 가장 바깥의 SELECT문
UNION Second or later SELECT statement in a UNION
UNION이 있을 때 두번째 이후의 SELECT 문
DEPENDENT UNION Second or later SELECT statement in a UNION, dependent on outer query
서브쿼리에서 UNION이 있을 때 서브쿼리의 두번째 이후의 SELECT 문이면서
메인쿼리의 영향을 받는 경우(메인테이블의 칼럼이 포함된 경우)
UNION RESULT Result of a UNION.
UNION으로 중복값을 제거한 경우
SUBQUERY First SELECT in subquery
서브쿼리
DEPENDENT SUBQUERY First SELECT in subquery, dependent on outer query
SUBQUERY가 메인 쿼리의 영향을 받는 경우(메인테이블의 칼럼이 포함된 경우)
DERIVED Derived table
FROM절에 작성된 서브쿼리
DEPENDENT DERIVED Derived table dependent on another table
FROM절에 작성된 서브쿼리가 메인 쿼리의 영향을 받는 경우
MATERIALIZED Materialized subquery
IN절의 서브쿼리가 임시 테이블을 만들고, 가공이나 조인을 수행한 경우
UNCACHEABLE SUBQUERY A subquery for which the result cannot be cached and must be re-evaluated for each row of the outer query
메모리에 있는 서브쿼리가 재사용되지 못한 경우(쿼리가 계속 변환이 일어남)
*서브쿼리문은 메모리에 탑재되어 재사용되는 특징이 있음.
UNCACHEABLE UNION The second or later select in a UNION that belongs to an uncacheable subquery (see UNCACHEABLE SUBQUERY)
재사용되지 않는 서브쿼리 내부에서 UNION 절이 사용된 경우,  UNION 이후의 SELECT문에 나타남.

 

조인 방법 / TYPE

TYPE 설명
SYSTEM 테이블에 데이터가 없거나 1개만 있는 경우
CONST 인덱스나 KEY를 이용해 1건의 데이터만 찾는 경우
EQ_REF JOIN시 DRIVEN TABLE에서 KEY나 인덱스를 이용해서 하나의 값만 찾아오는 경우
메인 테이블과 DRIVEN TABLE의 조인 수행시 JOIN 조건에 DRIVEN TABLE의 KEY나 UNIQUE NOT NULL 인덱스가 사용된 경우
REF JOIN시 DRIVEN TABLE에서 하나 이상의 값을 찾아오는 경우
메인 테이블과 DRIVEN TABLE의 조인 수행시 JOIN 조건에 DRIVEN TABLE의 KEY나 UNIQUE NOT NULL 인덱스가 사용되지 않은 경우
FULL_TEXT 텍스트 검색을 빠르게 처리하기 위해 FULL TEXT INDEX 를 사용하는 경우
REF_OR_NULL REF와 유사하지만 NULL을 포함해서 탐색하는 방식 (조인 조건에 IS NULL이 있는 경우)
INDEX_MERGE 인덱스 여러개가 동시에 사용된 경우
UNIQUE_SUBQUERY IN 서브쿼리에서 KEY나 UNIQUE NOT NULL 인덱스를 이용한 탐색이 일어난 경우
INDEX_SUBQUERY IN 서브쿼리에서 NONUNIQUE INDEX를 이용한 탐색이 일어난 경우
RANGE BETWEEN, IN, >, < 등 범위 조건이 사용된 경우
INDEX INDEX FULL SCAN, 인덱스를 모두 탐색한 경우
ALL TABLE FULL SCAN, 테이블을 모두 탐색한 경우

 

추가정보 / EXTRA

EXTRA 설명
DISTINCT 중복값이 제거된 경우
USING WHERE WHERE 조건에 의해 필터링된 경우
UNING TEMPERORY 임시 테이블을 생성한 경우(DISTINCT, GROUP BY, ORDER BY 구문에서 등장)
USING INDEX TABLE을 읽지 않고 인덱스만 읽은 경우
RECURSIVE 재귀를 사용한 경우
USING FILESORT 정렬이 수행된 경우( 정렬 데이터를 메모리에 올리고 사용한 경우)
USING JOIN BUFFER 조인 수행하기 위해 중간 데이터를 조인 버퍼에 담는 경우
(드라이빙 테이블 검색 결과를 조인 버퍼에 담고, 조인버퍼와 드리븐 테이블과의 조인을 수행.)
USING UNION 두 개 이상의 인덱스가 합집합으로 병합된 경우(OR 구문의 범위가 겹치지 않을때)
USING INTERSECT 두 개 이상의 인덱스가 교집합으로 병합된 경우(AND 조건)
USING SORT UNION 두 개 이상의 인덱스가 병합된 경우(OR 구문의 범위가 겹치는 경우)
USING INDEX CONDITION 외부의 필터링 조건을 내부로 전달해 처리할 데이터의 양을 줄이는 방식 (PUSH DOWN)
Using index for group-by  GROUP BY나 DISTINCT 연산일 때 인덱스로 정렬 작업을 수행한 경우
Using index for skip scan  INDEX SKIP SCAN을 사용한 경우
Not Exists left outer join으로 한쪽에 존재하지 않는 데이터를 검색한 경우

* 추가 정보 : Oracle, explain-extra-information, Explain Output Format, MySQL 8.0 Reference Manual

USING UNION

SELECT COUNT(*) FROM t1 WHERE key1 = 1 AND key2 = 1;

USING INTERSECTION

SELECT * FROM innodb_table
  WHERE primary_key < 10 AND key_col1 = 20;

USING SORT UNION

SELECT * FROM tbl_name
  WHERE key_col1 < 10 OR key_col2 < 20;

 NOT EXISTS

SELECT * FROM t1 LEFT JOIN t2 ON t1.id=t2.id
  WHERE t2.id IS NULL;

 

출처

양바른, 업무에 바로 쓰는 SQL 튜닝, 한빛미디어

Oracle, Explain Output Format, MySQL 8.0 Reference Manual

 

 

 

 

'DB > SQL' 카테고리의 다른 글

MySQL 쿼리 정리  (0) 2021.10.10
MYSQL SELECT 튜닝  (0) 2021.10.10
MySQL 데이터 타입 Data Types  (0) 2021.10.10
MYSQL 힌트  (0) 2021.10.07
ORACLE과 MYSQL의 차이점  (2) 2021.10.07