inline이 함수 호출의 부하를 줄여주는게 맞나요 ?

mastercho의 이미지

인라인을 쓰면 뭔가 빨라지겠지 않냐라는 생각에 무심코 다음과 같은 코드를

작성해 봤습니다


 inline int For_()

{

    static int array[7]={0,1,2,3,4,5,6};

    int result=0;

    for(int i=0; i < 7; ++i)

    {

        if( i > array[i])

            break;

 

        result += i;

    }

 

    return result;

}

 

 

int _tmain(int argc, _TCHAR* argv[])

{

    DWORD begin,end;

    const int mm = 200000;  

 

    begin = GetTickCount();

 

    int counter=0;

 

    for (i=0; i< mm*5; ++i)

    {

        counter += For_();

    }

 

    end = GetTickCount();

    printf(" Time : %d \n",end - begin);

 

    return 0;

}

측정 결과는 20 이 나오더군요 .......

그래서 line을 지워 봤습니다

그랬더니 10이 나오더랍니다 -_-;

좀 황당해서리......

분명 함수 호출을 100만번이나 수없이 때리기 때문에 함수 호출에 대한 부하가 클줄 알고

line을 적용했었지만 성능은 두배나 나빠졌습니다

VC++ 7.1 릴리즈 모드에서 테스트 했습니다 왜 그럴까요?

sangwoo의 이미지

인라인은 함수호출 오버헤드는 줄여주지만, 오브젝트 크기가 커지기 때문에
경우에 따라서는 부정적인 효과를 나타낸다고 들었습니다.

----
Let's shut up and code.

serat의 이미지

성능 측정 방법에 문제가 있어보입니다. 윈도우에서 GetTickCount()하면, 아마 기억에는 최소단위가 10으로 나왔던 것 같은데.. 10과 20이면, 오차 범위라고 봐야 할 것 같은데요.(실제 19와 20 차이일 수도 있습니다.) 프로그램 수행 순간의 다른 프로세스가 얼마나 동작했는 냐에도 영향을 받을 것 같구요..

시간 결과 값이 1000이나 10000단위 이상으로는 나오도록 반복횟수를 늘리고, 자기 프로세스 시간만 측정하고 resolution이 더 높은 API를 사용해야 할 듯 합니다.

저 정도 함수 길이면, cache안에 충분히 들어가서, inline을 한다고 해서 성능이 나빠질 것 같지는 않습니다.

inline이라는 keyword를 주어라도, 컴파일러가 무조건 inline으로 하지는 않습니다.(반대의 경우도 있습니다.) 실제로 inline되었는지는 assem 코드를 살펴봐야 할 듯합니다. 또, 함수를 inline할 때, static도 붙여주면, 함수가 현재 파일에서만 사용될 것이라고 알려주는 역할을 해서 컴파일러가 최적화하는데 도움을 줄 수 있습니다.

mastercho의 이미지

serat wrote:
성능 측정 방법에 문제가 있어보입니다. 윈도우에서 GetTickCount()하면, 아마 기억에는 최소단위가 10으로 나왔던 것 같은데.. 10과 20이면, 오차 범위라고 봐야 할 것 같은데요.(실제 19와 20 차이일 수도 있습니다.) 프로그램 수행 순간의 다른 프로세스가 얼마나 동작했는 냐에도 영향을 받을 것 같구요..

시간 결과 값이 1000이나 10000단위 이상으로는 나오도록 반복횟수를 늘리고, 자기 프로세스 시간만 측정하고 resolution이 더 높은 API를 사용해야 할 듯 합니다.

저 정도 함수 길이면, cache안에 충분히 들어가서, inline을 한다고 해서 성능이 나빠질 것 같지는 않습니다.

inline이라는 keyword를 주어라도, 컴파일러가 무조건 inline으로 하지는 않습니다.(반대의 경우도 있습니다.) 실제로 inline되었는지는 assem 코드를 살펴봐야 할 듯합니다. 또, 함수를 inline할 때, static도 붙여주면, 함수가 현재 파일에서만 사용될 것이라고 알려주는 역할을 해서 컴파일러가 최적화하는데 도움을 줄 수 있습니다.

반복해서 테스트 해봤습니다

오차 범위라 생각할수 있을거 같아 보이지만

반복해서 테스트 해보면 중간값이나 평균 값으로 거의 그렇게 나오기 때문에
이렇게 글을 올린것입니다

20번 반복해서 해서 정확히 같은 수가 계속해서 나왔기때문에
분명 차이가 있는게 맞습니다

그리고 디스 어셈으로 확인했지만

디버깅 모드에서는 inline을 무시하는거 같습니다

inline int getint()
{
static int i=0;
return i++;
}

이런 함수도 인라인이 되지 못하고 콜을 합니다

static 변수 때문에 문제인가 싶어 다시 int i=0로 바꿔봤는데도
마찬가지네요

승자는 자기보다 우월한 사람을 보면 존경심을 갖고 그로부터 배울 점을 찾지만 패자는 자기보다 우월한 사람을 만나면 질투심을 갖고 어디 구멍난 곳이 없는지 찾는다.
- 하비스

mastercho의 이미지

혹시나 하고 값을 올려 했더니만

오차 범위가 맞는거 같습니다

이런 -_-;

지금 해보니 값이 이상하게 비슷하게 나오네요

것참..... -_-;

신기한건 제가 테스트 해본 모든 함수들이 inline 붙이나 안붙이나 릴리즈 모드나 디버깅 모드 둘다 똑같은 어셈 코드를 내더군요

그리고 제가 한번 테스트 한 결과를 다시 종합해 보겠습니다

일단 결론은 VC++ 7.1 컴파일러가 많이 영리한거 같습니다

릴리즈 모드에서 확인 결과 위에서 테스트 한 함수 For_() 가

내부에 for문도 들어있고 코드량이 아주 짧은거 같지않은데도

inline을 붙이지 않 않고도 inline처리 되어 버린거 같습니다

[디스 어셈블 결과]

그리고 여러 함수들을 만들어 보고 사용했는데

release모드에서는 왠만하면 다 inline처리 해버리는거 같더군요

따라서 사용자가 inline 키워드를 따로 줄 필요없이

inline 자체는 그냥 컴파일러에게 위임해도 좋지 않을까 하는 생각이 들었습니다

승자는 자기보다 우월한 사람을 보면 존경심을 갖고 그로부터 배울 점을 찾지만 패자는 자기보다 우월한 사람을 만나면 질투심을 갖고 어디 구멍난 곳이 없는지 찾는다.
- 하비스

hb_kim의 이미지

비교적 간단하고 크기가 작은 함수이면서, 전달인수가 많은 경우를 테스트해보시면 어떨지요?

hb_kim의 이미지

mastercho wrote:
릴리즈 모드에서 확인 결과 위에서 테스트 한 함수 For_() 가

내부에 for문도 들어있고 코드량이 아주 짧은거 같지않은데도

inline을 붙이지 않 않고도 inline처리 되어 버린거 같습니다

[디스 어셈블 결과]

그 함수를 여러 군데에서 호출해도 그렇게 될까요?

정태영의 이미지

그정도라면 매크로로;;
;;;;

오랫동안 꿈을 그리는 사람은 그 꿈을 닮아간다...

http://mytears.org ~(~_~)~
나 한줄기 바람처럼..