프로그램 최적화의 90/10 규칙의 의미는 무엇입니까?


67

Wikipedia에 따르면, 프로그램 최적화의 90/10 규칙에 따르면 "프로그램 실행 시간의 90 %가 코드의 10 %를 실행하는 데 소비됩니다"라고되어 있습니다 (두 번째 단락 참조 ).

나는 이것을 정말로 이해하지 못한다. 이것이 정확히 무엇을 의미합니까? 실행 시간의 90 %를 코드의 10 % 만 실행하는 데 어떻게 사용할 수 있습니까? 그러면 코드의 다른 90 %는 어떻습니까? 시간의 10 % 만에 어떻게 실행될 수 있습니까?


50
코드의 일부는 다른 부분보다 더 자주 실행될 수 있습니다. 이것이 루프의 목적입니다. 실제로, 거의 항상 일부가 실행되는 방식으로 다른 사람보다 더 자주.
Kilian Foth

147
소프트웨어 프로젝트 기간 동안 90/10 규칙이 들릴 때까지 기다리십시오.“프로젝트의 90 %가 할당 된 시간의 처음 90 %를 차지합니다. 프로젝트의 마지막 10 %는 할당 된 시간의 다른 90 %를 차지합니다.”
Paul D. Waite

3
여기서 혼동 : "실행 시간이 소요됩니다". 고려하십시오 a++; for(i=0;i<100;i++){b++;} for(i=0;i<100;i++){print(xyz);}. 물론 첫 번째 for-loop는 첫 번째 문보다 훨씬 더 많이 소비하지만 두 번째 for-loop는 첫 번째 for-loop보다 ~ 1000x 더 많은 시간을 소비 하지만 실행하지는 않습니다 . 그것은 소비 인쇄 기다리고 . 따라서 실행 시간과 코드가 담당하는 시간 사이에는 차이 가 있습니다 .
Mike Dunlavey

32
@ Paul_D._Waite 나는 프로젝트의 90 %가 시간의 90 %를, 왼쪽의 90 %가 시간의 또 다른 90 %를 소요하고, 비 수렴 시리즈를 다운하여 프로젝트가 없다는 결론에 도달했다고 생각했습니다. 무한한 시간 내에 완료되거나 완전히 디버깅됩니다.
nigel222

9
실제 예를 들어, 내가 연구 한 (과학적 모델) 두 코드는 모델을 읽고 설정하는 데 많은 양의 코드 (~ 10K 줄)를 사용한 다음 실제 계산을 수행하기 위해 수백 줄을 반복했습니다. 그러나 그 짧은 루프는 n ^ 4 (수천 개의 시간 단계를 반복하는 세 개의 공간 크기)이므로 계산하는 데 며칠이 걸렸습니다. 그래서 실제 비율은 아마 같은 99 % / 1 % :-)이었다
jamesqf

답변:


184

여기에는 두 가지 기본 원칙이 있습니다.

  • 일부 코드는 다른 코드보다 훨씬 자주 실행됩니다. 예를 들어, 일부 오류 처리 코드는 사용되지 않을 수 있습니다. 일부 코드는 프로그램을 시작할 때만 실행됩니다. 프로그램이 실행되는 동안 다른 코드가 계속해서 실행됩니다.
  • 일부 코드는 다른 코드보다 실행하는 데 훨씬 오래 걸립니다 . 예를 들어 데이터베이스에서 쿼리를 실행하거나 인터넷에서 파일을 가져 오는 단일 행은 수백만 번의 수학 연산보다 오래 걸릴 수 있습니다.

90/10 규칙은 문자 그대로 사실이 아닙니다. 그것은 프로그램에 따라 다릅니다 (그리고 나는 90과 10의 특정 숫자에 대한 근거가 전혀 없다고 의심합니다; 누군가가 아마도 그것들을 얇은 공기에서 끌어 냈습니다). 그러나 요점은 프로그램을 더 빨리 실행 해야하는 경우 적은 수의 라인만이 그렇게하는 데 중요하다는 것입니다. 소프트웨어의 느린 부분을 식별하는 것이 종종 최적화의 가장 큰 부분입니다.

이것은 중요한 통찰력이며 새로운 개발자에게 반 직관적으로 보이는 결정이 종종 정확할 수 있음을 의미합니다. 예를 들면 다음과 같습니다.

  • 멍청하고 단순한 방법으로 작업을 수행하더라도 "더 나은" 작업을 수행 할 가치가없는 코드가 많이 있습니다 . XYZ 애플리케이션에 대해보다 효율적인 검색 알고리즘을 작성할 수 있습니까? 그렇습니다. 그러나 수천 개의 값이 있더라도 실제로 모든 값을 간단히 비교하는 데는 시간이 걸립니다. 따라서 가치가 없습니다. 학위 프로그램에서 "정확한"(가장 효율적인) 알고리즘을 작성하는 데 많은 시간을 소비했기 때문에 새로운 개발자는 불필요한 최적화를 피하기가 어려울 수 있습니다. 그러나 실제 세계에서 올바른 알고리즘은 작동하고 충분히 빠르게 작동하는 알고리즘입니다.
  • 코드를 훨씬 더 길고 복잡하게 만드는 변경은 여전히 ​​성능상의 승리 일 수 있습니다. 예를 들어, 응용 프로그램 FOO에서는 단일 데이터베이스 호출을 피하기 위해 수백 줄의 새로운 논리를 추가하는 것이 좋습니다.

6
특히 정렬 기능과 같은 기능을 사용하면 우아한 알고가 완벽하게 작동하고 버그가없는 것보다 모든 경우에 바보 같은 단순한 알고가 올바른 작업을 수행하는 것이 훨씬 빠르며 (개발 시간에) 빠릅니다. (아카데 마 외부에서 분류 알고리즘을 작성해야하는 유일한 이유는 라이브러리를 구축하거나 하나가없는 플랫폼에서 작업하는 경우에…)
StarWeaver

5
난 당신에 대한 링크를 추가 할 필요가 있다고 생각 shouldioptimize.com :
이반 Kolmychek

13
나는 90/10는 잘 알려진 20 분의 80 파레토 원리에서 오는 생각 en.wikipedia.org/wiki/Pareto_principle이
fernando.reyes

2
@StarWeaver 그렇기 때문에 C ++처럼 엉터리 버블 정렬보다 쉽고 효율적으로 초 고효율 정렬을 작성하는 언어가 중요합니다. 이러한 "미리 패키징 된"알고리즘 및 코드는 사용 시점에서 복잡성을 유발하지 않으면 서 실제로 크게 최적화 될 수 있습니다.
Yakk

6
@IvanKolmychek 그 사이트는 오해의 소지가 있습니다. 물론 이러한 종류의 비용 분석은 고려해야 할 한 가지 요소이지만 사용자 경험과 같은 다른 요소가 있습니다. 최적화하지 않으면 많은 돈을 저축 할 수 있지만 사람들이 사이트를 실망하게하면 많은 수입을 놓칠 수도 있습니다.
jpmc26

21

이것은 자연의 법칙이 아니라 폭 넓은 경험으로 태어난 경험 법칙입니다. 80/20 규칙이라고도하며 대략적인 근사치입니다.

루프, 분기 및 기타 흐름 제어

if가있는 각 장소에는 다른 지점보다 더 자주 사용되는 하나의 지점이 있습니다. 따라서 다른 부분이 아닌 프로그램의 해당 부분을 실행하는 데 더 많은 실행 시간이 소비됩니다.

루프가 두 번 이상 실행되는 각 장소에는 주변 코드보다 더 많이 실행되는 코드가 있습니다. 따라서 더 많은 시간이 소요됩니다.

예를 들어 다음을 고려하십시오.

def DoSomeWork():
    for i in range(1000000):
        DoWork(i)
    except WorkExeption:
        print("Oh No!")

여기서 print("Oh No!")의지는 최대 한 번만 실행되며, 결코 그렇지는 않지만 종종 DoWork(i)백만 번 발생합니다.


7
이것을 80/20 규칙이라고 부르면 파레토 원리 와 혼동 될 수 있는데, 이는 단지 프로그래밍보다 더 광범위하게 적용됩니다. 어쩌면 90과 10은 의미 상 겹치지 않는 편리한 숫자 일 것입니다.
trichoplax

29
파레토 교장의 사례입니다. 두 숫자 쌍 모두 동일합니다
Caleth

2
파레토 원리에서 80/20 분할에 대한 수학적 기초가 있습니다. 그들은 "많은"과 "작은"을 나타내는 상상의 인물이 아닙니다.
Moyli

1
@Moyli-그렇습니다. "80/20 스플릿에는 수학적 기초가 있습니다 ..."그러나 실제 세계에서는 결코 우연히 80/20이 될 수 없습니다.
Kevin Fegan

2
@trichoplax 파레토 원리는 여기에 아주 잘 적용됩니다. 원인 (상기 코드 라인)의 20 %는 80 % 효과 (런타임)을 유발
njzk2

16

루프.

나는 거기에서 멈추고 싶다! :-)

이 프로그램을 고려

1. do_something

2. loop 10 times
3.    do_another_thing

4.    loop 5 times
5.        do_more_stuff

행 1은 한 번 실행되고 행 3은 10 번 실행됩니다. 각 줄을 차례로 보면서

1 1   0.8%
2 10  8.3%
3 10  8.3%
4 50 41.3%
5 50 41.3%

두 줄이 실행 시간의 83 %를 차지합니다 (모든 줄을 실행하는 데 거의 같은 시간이 걸린다고 가정하면 프로그램의 40 %가 80 % 이상을 차지합니다).

실제 사례가 더 커질수록 이것은 줄어듦에 따라 적은 양의 라인 만이 많은 런타임을 차지합니다.

90/10 규칙 (또는 때때로 80/20으로 표시)은 "거의 규칙"입니다.

파레토 원리 참조


2
거의 사실이라고 말하는 대신, 많은 경우에, 최소한 90 %의 시간이 최대 10 % 의 작은 코드 실행하는 데 소비 될 것이라고 말합니다 . 분명히 모든 부분이 실행하는 데 거의 같은 시간을 소비하는 프로그램을 가질 수는 있지만 드문 일입니다.
supercat

파레토 원리를 참조하면 +1 이 환상적인 Vsauce 비디오 에서보다 자세한 설명을 볼 수 있습니다 .
Radu Murzea

5

실행 시간에 대해서만 물었을 때이 예제가 도움이 될 수 있습니다.

int main() {
    sleep(90); // approximately 10% of the program.
    // other 90% of the program:
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    sleep(1);
    return 0;
}

좀 더 심각하다면 실제 코드에서는 거의 항상 루프 대신 무거운 함수를 호출 sleep(90);하지만 나머지 10 %는 단일 패스 계산을 수행합니다.

또 다른 예는 일부 HA 서비스의 오류 처리입니다. 고 가용성 서비스는 정상적인 조건에서 무한한 시간 동안 작동하도록 설계되었습니다 . 일반적으로 99 %의 시간 동안 작동하지만 때때로 오류가 발생하면 일부 오류 처리 및 복구가 실행되므로 서비스 자체보다 논리적으로 더 복잡 할 수 있습니다.


니스, 나는 누군가 가이 극단적 인 예를 게시하기를 바랐습니다.
djechlin

3

90/10의 추론은 코드의 일부가 다른 코드보다 반복되거나 더 많이 사용됨을 의미합니다. 이것은 종종 10 %의 코드에 개발 / 최적화 노력의 90 %를 집중시켜야한다는 것을 제안하는 데 사용됩니다.

Microsoft Word 또는 OpenOffice 와 같은 일반적인 텍스트 프로세서를 생각해보십시오 .

  • 환경 설정 대화 상자는 많이 사용되지 않습니다.
  • 문자를 그리는 서브 루틴은 항상 사용됩니다.

이 말은 경영 과학에도 사용됩니다 ... 이것은 인생 자체에 대한 교훈입니다 ... 의미 : 더 많은 결과를 얻을 수있는 대부분의 노력에 집중하십시오.


6
Microsoft Word가 단순하다면 복잡한 것의 예는 무엇입니까?
Peter Mortensen

말이 안되는 @PeterMortensen.
그레이트 덕

@PeterMortensen Emacs입니다.
muru

2

다음과 같은 프로그램을 상상해보십시오.

print "H"
print "e"
print "l"
print "l"
print "o"
for i=0 to 1,000,000
    print "How long now?"
next
print "B"
print "y"
print "e"

여기에 11 개 중 3 개가 for 루프 인 곳에 11 개의 라인이 있고,이 작은 코드 조각에 얼마나 많은 시간이 소비되는지 주목하십시오. 다른 8 줄은 단지 하나의 문자를 인쇄하는 동안 꽤 많습니다. 따라서 일부 코드는 짧을 수 있지만 코드가 얼마나 자주 실행되고 얼마나 오래 걸리는지 알려주지 않습니다.


0

다른 위대한 답변에서 언급했듯이 루핑 외에도 고려해야 할 DRY 원칙이 있습니다. 잘 작성된 Object Oriented 코드에는 재사용 가능한 부분이 많이 있습니다. 정의에 따라 재사용되는 부분은 한 번만 실행되는 것보다 두 배 이상 자주 사용됩니다. OO 코드가 많으면 몇 가지 클래스와 메서드를 여러 번 재사용하고 다른 코드는 한 번만 재사용 할 수 있습니다.

다른 답변에서 언급했듯이 한 번만 사용되는 코드를 개선하는 것보다 더 자주 사용되는 코드를 만드는 데 노력을 기울이는 것이 좋습니다.


2
많은 코드를 재사용 할 수 있지만 모든 코드는 자주 실행되지 않을 수 있습니다 (여전히 결정적 임).
Peter Mortensen

@PeterMortensen "중요하지만 자주는 아니다"는 "거의 1 초마다 재사용하고 가능한 빨리해야합니다"
The Great Duck

@ TheGreatDuck 그리고 나는 그것이 그가 의미 한 바라고 생각하지 않습니다. 당신이 있기 때문에 할 수 자주 실행되는 코드를 가지고 있지만, 당신은 가능한 한 빨리 일어날합니다. 예를 들어, 오류 복구를하겠습니다. 응용 프로그램에 따라 시스템이 다시 작동하는 데 약간의 시간 (5 분, 1 시간 등)이 걸릴 수 있습니다. 그러나 비행 시스템 에 오류가 발생하면 가능한 한 빨리 시스템을 원합니다. 그렇지 않은 경우 문자 그대로 의미에서 "다운"및 "충돌"합니다.
VLAZ

이것은 DRY에 OO가 필요하다는 것을 암시하는 것 같습니다. 물론 그렇지 않습니다. 재사용은 무료 기능 등으로 동등하게 촉진됩니다.
underscore_d

@vlaz는 사실이지만 비행기 안에서는 모든 것이 빠르게 진행되어야합니다.
그레이트 덕

0

그것은 규칙이 아닙니다. 그것은 Wikipedia를 편집 한 몇 사람입니다. 다른 맥락에서 더 확고하게 확립 된 파레토 원리와 비교하십시오. 이 "규칙"의 정확성에 대해 어떤 연구가 이루어 졌는지보고 싶습니다.

그러나 기본적으로 귀하의 질문에 대한 답변은 일부 코드가 다른 코드보다 훨씬 자주 실행된다는 것입니다. 루프가 종종 그 이유입니다. 다른 이유는 웹 서비스 나 저장 매체와 같은 외부 자원에 대한 호출이 시간이 많이 걸리는 것입니다.


사람들이 경험적으로 일반적으로 사용하는 것은 합법적 인 것입니다.
그레이트 덕

이것이 일반적으로 널리 사용된다고 제안하는 경우 그 증거도보고 싶습니다. 아니면 또 다른 의견이 허공에서 빠져 나왔지만 사실로 암시되어 있습니까?
Brad Thomas

wikipedia 기사 를 실제로 읽으면 asker가 인용 한 인용문에 amazon.com/Every-Computer-Performance-Book-Computers/dp/ 인용문이 있다는 것을 알 수 있습니다. 개인적으로 사용하는 것을 본 적이 없습니다. 하지만 당신은 게시물에 무례하고 제 의견으로는 기각되어서 응답했습니다. 분명히 10 %는 누군가가 만든 숫자입니다. 프로그램을 비효율적으로 만들어 원하는 수를 만들 수 있습니다. 그러나 소프트웨어 엔지니어링에 사용되는 용어인지 여부는 여기에 얼마나 많은 사람들이 존재하는지에 대해 논란의 여지가 없습니다.
그레이트 오리

글쎄, 난 그냥 책을 구입하려고하지 않을 것입니다 단지 그것이 참조하는 연구를 참조하십시오 ... 당신은 증거를 보여주는 인용을 게시 할 수 있습니까? 아니면 실제로 아무도 보지 못했습니까?
Brad Thomas

1
@BradThomas : Wikipedia를 편집하는 사람이 90-10 규칙을 발명했다는 이론에 대한 증거는 Wikipedia가 존재하기 몇 년 전에 90과 10의 숫자로 널리 인용되었다는 것입니다. 실제 원칙은 정확히 코드의 10 %가 런타임의 90 %를 차지하는 것이 아니라 대부분의 프로그램에서 코드의 10 % 이하가 실행 시간 의 큰 부분을 차지한다는 것입니다. -90 % 이상 코드의 작은 부분의 성능도 10 %의 개선이 다른 모든 것들의 1000 배 향상보다 전체 실행 시간을 줄일 수있다.
supercat

0

이것은 "파레토 원리"를 재 해석 한 것으로 "많은 사건의 경우 약 80 %의 효과가 원인의 20 %에서 비롯된 것입니다."라고도하며 80/20 규칙이라고도합니다. 이 규칙은 대부분 경제학에 적용되므로 프로그래밍 목적으로 사용되는 것이 좋습니다.

오랜 기간 동안 관찰 된 패턴 일뿐입니다.

다음은 이와 같은 패턴에 대한 매우 유용한 비디오이며 파레토 원리도 설명합니다.

https://www.youtube.com/watch?v=fCn8zs912OE&ab_channel=Vsauce

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.