스위치 속도 대
스위치 문은 일반적으로 컴파일러 최적화로 인해 동등한 if-else-if 문보다 빠릅니다 (예 :이 기사 에서 설명 ).
이 최적화는 실제로 어떻게 작동합니까? 누구든지 좋은 설명이 있습니까?
컴파일러는 해당되는 경우 점프 테이블을 빌드 할 수 있습니다. 예를 들어 리플렉터를 사용하여 생성 된 코드를 보면 문자열의 거대한 스위치에 대해 실제로 해시 테이블을 사용하여 코드를 전달하는 코드가 컴파일러에서 생성됩니다. 해시 테이블은 문자열을 키로 사용하고 case
코드에 값으로 위임 합니다.
이것은 많은 체인 if
테스트 보다 점근 적으로 더 나은 런타임 을 가지며 비교적 적은 수의 문자열에서도 실제로 더 빠릅니다.
이것은 일반적으로 if..else if ..
사람에 의해 switch 문 으로 간단 하게 변환 될 수 있는 시퀀스 를 만나는 현대의 모든 컴파일러와 마찬가지로 약간 단순화됩니다 . 컴파일러도 마찬가지입니다. 그러나 추가 재미를 더하기 위해 컴파일러는 구문에 의해 제한되지 않으므로 범위, 단일 대상 등이 혼합되어있는 내부적으로 "스위치"와 같은 명령문을 생성 할 수 있으며 스위치와 if 모두에 대해이를 수행 할 수 있습니다. .else 문.
Konrad의 답변에 대한 확장은 컴파일러가 점프 테이블을 생성 할 수 있지만 반드시 보장되는 것은 아닙니다 (바람직하지 않음). 다양한 이유로 점프 테이블은 최신 프로세서의 분기 예측 자에게 나쁜 일을하고 테이블 자체는 예를 들어 동작을 캐시하기 위해 나쁜 일을합니다.
switch(a) { case 0: ...; break; case 1: ...; break; }
컴파일러가이를 위해 점프 테이블을 실제로 생성 한 경우 if..else if..
분기 예측을 물리 치는 점프 테이블 때문에 대체 스타일 코드 보다 느릴 수 있습니다 .
불일치 통계는 좋지 않을 수 있습니다.
실제로 소스를 다운로드하면 if 및 switch 모두에서 일치하는 값 없음 값이 21 인 것으로 알려져 있습니다. 컴파일러는 항상 어떤 명령문을 실행해야하는지 알고 추상화 할 수 있어야하며 CPU는 올바르게 분기 예측할 수 있어야합니다.
더 흥미로운 경우는 제 생각에 모든 사례가 깨지는 것은 아니지만 실험의 범위가 아닐 수도 있습니다.
스위치 / 케이스 문은 일반적으로 1 수준 깊이가 더 빠를 수 있지만, 2 개 이상 들어가기 시작하면 스위치 / 케이스 문은 중첩 된 if / else 문보다 2-3 배의 시간이 걸립니다.
이 기사에는 이러한 명령문이 중첩 될 때의 속도 차이를 강조하는 몇 가지 속도 비교 가 있습니다.
예를 들어, 테스트에 따라 다음과 같은 샘플 코드를 작성하십시오.
if (x % 3 == 0)
if (y % 3 == 0)
total += 3;
else if (y % 3 == 1)
total += 2;
else if (y % 3 == 2)
total += 1;
else
total += 0;
else if (x % 3 == 1)
if (y % 3 == 0)
total += 3;
else if (y % 3 == 1)
total += 2;
else if (y % 3 == 2)
total += 1;
else
total += 0;
else if (x % 3 == 2)
if (y % 3 == 0)
total += 3;
else if (y % 3 == 1)
total += 2;
else if (y % 3 == 2)
total += 1;
else
total += 0;
else
if (y % 3 == 0)
total += 3;
else if (y % 3 == 1)
total += 2;
else if (y % 3 == 2)
total += 1;
else
total += 0;
마무리 의 절반 에 해당하는 스위치 / 케이스 문을 실행하는 데 걸린 시간 :
switch (x % 3)
{
case 0:
switch (y % 3)
{
case 0: total += 3;
break;
case 1: total += 2;
break;
case 2: total += 1;
break;
default: total += 0;
break;
}
break;
case 1:
switch (y % 3)
{
case 0: total += 3;
break;
case 1: total += 2;
break;
case 2: total += 1;
break;
default: total += 0;
break;
}
break;
case 2:
switch (y % 3)
{
case 0: total += 3;
break;
case 1: total += 2;
break;
case 2: total += 1;
break;
default: total += 0;
break;
}
break;
default:
switch (y % 3)
{
case 0: total += 3;
break;
case 1: total += 2;
break;
case 2: total += 1;
break;
default: total += 0;
break;
}
break;
}
예, 그것은 기본적인 예이지만 요점을 보여줍니다.
따라서 결론은 하나의 수준에 불과한 단순한 유형의 경우 switch / case를 사용할 수 있지만 더 복잡한 비교 및 여러 개의 중첩 된 수준의 경우 고전적인 if / else 구문을 사용합니까?
if over 경우의 유일한 장점은 첫 번째 경우의 발생 빈도가 눈에 띄게 증가하는 경우입니다.
임계 값이 어디에 있는지 정확히 모르지만 첫 번째 "거의 항상"첫 번째 테스트를 통과하지 않으면 대소 문자 구문을 사용합니다.
참고 URL : https://stackoverflow.com/questions/445067/if-vs-switch-speed
'Programming' 카테고리의 다른 글
Intellij Idea에서 사용되지 않는 모든 클래스를 어떻게 찾습니까? (0) | 2020.08.05 |
---|---|
iPython 노트북에서 올바른 디버그 방법은 무엇입니까? (0) | 2020.08.05 |
.aspx와 .ashx MAIN의 차이점 (0) | 2020.08.05 |
간헐적 인 log4net RollingFileAppender 잠금 파일 문제 (0) | 2020.08.05 |
pycharm 실행 속도가 느림 (0) | 2020.08.05 |