mysql select 문 질문입니다.

   조회 4146   추천 0    

 안녕하세요


mysql 에서 아래 쿼리를 실행했습니다.

SELECT * FROM nn.dataset_2day_normalize_60 where date >20120331 and date < 20150101;


DB Type은 MyISam 입니다.

index는 date에 걸어 놓았고

Data는 column 이 1684개 입니다. (자료형은 Float 입니다.)

전체 테이블은 9G 정도 되는데

위의 쿼리 시행 시간이 30분을 돌려도 끝나지 않습니다.

계속 놔두면 언젠가 끝나기는 합니다.


어떻게 해야 속도가 빨라질까요?

짧은글 일수록 신중하게.
똥떵어리 2017-04
아래 명령어로 먼저 실행계획을 확인해보시기 바랍니다.
EXPLAIN SELECT * FROM nn.dataset_2day_normalize_60 where date >20120331 and date < 20150101;

실제로 인덱스가 잘 작동하는지 확인하신후 문제가 된다면 Force Index등으로 강제로 설정할 필요도 있습니다.
그리고 SELECT 조회 컬럼은 필요한 컬럼만 명시하는게 좋습니다.
     
감사합니다
explain을 먼저 해 봐야겠네요
     
explain SELECT * FROM nn.dataset_2day_normalize_60 force index (idx1) where date > 20141231;

id 1
select_type : Simple
Table : dataset_2day_normalize_60
partitions : null
type : range
possible_keys :idx1
Key : idx1
key_len : 4
ref : null
rows: 639588
filtered : 100.00
Extra : using index condition

으로 나오는데도 느립니다. (idx1가 date index 입니다.)

또 해볼 수 있는 것이 있을까요?
          
DAP박인호 2017-04
force index (idx1) 이것 빼고 explain 해 보세요.
원래 index 안타는데 이것넣어 강제로 태우면 오히려 느려질 수 있습니다.
date >20120331 and date < 20150101 이 조건으로 봐서는 기간 조건이 매우 넓어
index를 안탈 것으로 보이거든요.
index를 만들었다고 해도
전체 건수에 비해 select 건수가 일정% 보다 많으면
full select 가
빨라 그렇게 처리 됩니다.
DAP박인호 2017-04
컬럼수가 1684개요?
분할이 필요해 보이네요.
where 조건 범위를 봐서
Index를 안탈 가능성도 보이네요.
     
이런 조건에서 인덱스를 사용할 수 있는 방법이 있을까요?
          
DAP박인호 2017-04
where 조건을 index가 탈 수 있을 정도로 줄여서
반복 실행 하는 것이 더 빠를 수 있습니다

장기적으로는
테이블을 정규화(수직분할 포함), 파티셔닝이 필요해 보입니다.
잔다르크 2017-04
인덱스가 제대로 걸려 있으면 초 단위 미만에서 답이 나와야 할것 같은데요?
     
지금은 거의 40~50분 걸립니다...
한방인생 2017-04
SELECT 할때매번 1684개의 컬럼 데이터가 다 필요하신건가요?

WHERE 절에 해당하는 데이터랑 idx만 남겨 놓고, 분리되어 있는 테이블에서 나머지 컬럼 값을 수집할 수 있도록 구성하면 몇 초도 안 걸릴 문제 같습니다.
가능하시면 DB를 SSD나 좀 더 빠른 환경으로 인프라 환경을 바꿔 보시는 것도 방법일 것 같습니다.
     
계속 서비스 되는게 아니라
1회 성으로 자료를 만드는 중이어서
전체 데이터는 모두 필요한 상황입니다.
DB는 SSD에 올라가 있습니다
아니 무슨 테이블이 옆으로 자라나요?
잔다르크 2017-04
쪽지 주신 내용을 보면 인덱스 처리 되지 않고 있습니다.
     
예 그래서 Force를 했는데
위에 답변 주신 것 보니까 강제 Force는 오히려 느릴 수 있다로 하시더라고요.

숫자를 줄여서 여러번 하는게 방법일것 같습니다.
김제연 2017-04
select a.*
from (
SELECT id값
FROM nn.dataset_2day_normalize_60 where date >20120331 and date < 20150101
) b join nn.dataset_2day_normalize_60 a on b.id값 = a.id값

이렇게 한번 해보세요
     
PK 가 다중키 ID를 이렇게 쓰면 안되지요?

select a.*
from (
SELECT code, date
FROM nn.dataset_2day_normalize_60 where date >20120331 and date < 20150101
) b join nn.dataset_2day_normalize_60 a on ( (b.code = a.code) and (b.date = a.date) )
          
김제연 2017-04
일단 해보시면 될것 같은데요 . 제가 초보라 .. 다중칼럼pk 는 안써봤네요 ..
               
일단은 범위를 줄여서 해 봤는데

select a.*
from (
SELECT code, date
FROM nn.dataset_2day_normalize_60 where date >= 20120101 and date < 20120201
) b join nn.dataset_2day_normalize_60 a on ((b.code = a.code) and (b.date = a.date));

보다

SELECT * FROM nn.dataset_2day_normalize_60 where date >= 20120101 and date < 20120201;
가 빠른 것 같습니다.
DAP박인호 2017-04
1회성이고 전체 데이터가 모두 필요한 경우면
월단위 정도로 where 조건 줄여서 반복 실행하시는 것이
가장 빨리 진행할 수 있을 것으로 보입니다.
잔다르크 2017-04
인덱싱 되어 있다고 생각하지만 실제로는 안되어 있는것인지 아니면 인덱싱 되어 있지만 인덱스를 타지 않고 쿼리 되는것인지 확인 해봐야 할 것 같습니다.

SHOW INDEX FROM nn.dataset_2day_normalize_60 결과 올려줘보세요
     
쪽지로 보내드렸습니다.
도와주셔서 감사합니다.


QnA
제목Page 2014/5731
2014-05   5267742   정은준1
2015-12   1792766   백메가
2016-05   4516   geniefix
2014-05   4516   황진우
2014-05   4516   막판대장
2020-08   4516   공학123
2016-08   4516   Jjun
2016-04   4516   안형곤
2021-03   4516   이희권
2022-10   4516   응무소주
2013-12   4516   박성만
2017-01   4516   김정언
2015-01   4516   아름다운노을
2016-05   4516   띠로리
2015-03   4516   snflzhdj
2015-09   4516   김건우
2020-11   4516   가을햇살71
2020-11   4516   나나나나나
2015-12   4516   김건우
2014-01   4516   김승현
2017-10   4516   이니이니
2018-02   4516   김건우