2010-08-04 2 views
3

아래의 코드를 참조하십시오 :수없는

typedef void (*TimerCallback)(int RequestID_in, void* AdditionalParameter_in); 
class MyTimer 
{ 
    public: 
     MyTimer(){} 
     bool schedule(int Interval_in, TimerCallback TimerCallback_in, void* AdditionalParameter_in) 
     { 
      //some logic 
      return true; 
     } 
}; 

namespace 
{ 
    template <class T> 
    void myTimerFunc(int RequestID_in, void* AdditionalParameter_in) 
    { 
     MyLogic<T>* pLogic = static_cast<MyLogic<T>*>(AdditionalParameter_in); 
     if(pLogic) 
     { 
      //do something 
     } 
    } 
} 

template <class T> 
class MyLogic 
{ 
public: 
    MyLogic(){} 

    void testMe() 
    { 
     MyTimer aTimer; 
     aTimer.schedule(10, myTimerFunc<T>, this); 
    } 
}; 

int main() 
{ 
    MyLogic<int> myLogic; 
    myLogic.testMe(); 
} 

내가 VC6 컴파일러를 사용하고 컴파일러 오류 다음과 같은 예외 : 나는 비주얼이 코드를 테스트

error C2664: 'schedule' : cannot convert parameter 2 from 'void (int,void *)' to 'void (__cdecl *)(int,void *)' None of the functions with this name in scope match the target type E:\test\BTest\BTest.cpp(46) : while compiling class-template member function 'void __thiscall MyLogic::testMe(void)'

을 Studio 2008 및 아무 문제없이 잘 작동합니다.

VC6은 오래된 컴파일러이지만 내 프로젝트 소스 코드 (레거시)는 VC6으로 컴파일되어 있습니다.

따라서이 코드를 컴파일 할 수있는 방법은 없습니까?

typedef void (__stdcall *TimerCallback)(int RequestID_in, void* AdditionalParameter_in); 

나는 이유를 모르겠어요,하지만 오류 메시지가 제안되는 내용은 다음과 같습니다

+0

태그가 "6"이면 VC6을 의미합니까? – codymanix

+0

예. 나는 바뀔 것이다. –

+0

with '& myTimerFunc ', 작동합니까? – Scharron

답변

0

나는 당신이 거기에 __stdcall을 놓치고있어 생각합니다. 아마도 __cdecl 대신 __stdcall이라고 가정하는 컴파일러 매개 변수가 있거나 그 반대의 경우 일 수 있습니다.

+0

을 참조하십시오. 기본 호출 규칙 __cdecl을 사용해도이 문제가 발생하지 않습니다. 컴파일러는'void (__cdecl *) (int, void *)'가'void (*) (int, void *) '와 같은 타입이 아님을 더 이상 알지 못합니다. –

+0

수동으로 함수에 __cdecl을 설정해 보았습니까? – Puppy

+0

그 중 하나가 작동하지 않습니다. 나는 이것을 확인하기 위해 OP의 코드로 VS6을 해고했다. 그것은 컴파일러 버그 - 내 대답을 참조하십시오. –

1

모두 Visual Studio 버전 템플릿 기능을 함수 포인터로 변환/변환해야 할 때 발작을 일으켰습니다.

이 myTimerFunc의 유형이 여기에 변경되지 않습니다, 비주얼 스튜디오 6주의에서 컴파일
template<class T> 
T id(T t) 
{ 
    return t; 
} 

template <class T> 
class MyLogic 
{ 
public: 
    MyLogic(){} 

    void testMe() 
    { 
     MyTimer aTimer; 
     aTimer.schedule(10, id(myTimerFunc<T>), this); 
     //------------------^^(   ) 
    } 
}; 

, 그것은 단지 도움이 : 내가 사용하는 해결 방법은, 인수 변경를 반환하는 id() 기능을 사용하는 것입니다 사물을 해결하는 컴파일러.

+0

이 코드는 VS2010에서 제대로 컴파일됩니다. VS2008에서도 마찬가지 일 것이라고 예상하고 있습니다. – Puppy

+0

VS2010은 훌륭하기 때문에 아마 이것을 분류했습니다. 2008 년에는 여기를보십시오 : http://stackoverflow.com/questions/3395468/overloading-operator-to- accept-a-template-function 비슷한 문제 (템플릿 함수를 함수 포인터로 변환). OP에서 답변에 대한 내 해결 방법을 선택했습니다. 또한 모든 코드가 동일한 코드에 속한다고 말하는 것은 아닙니다. 이런 종류의 변환은 VS에서 문제가되는 경향이 있습니다. –

+0

또한 downvote에 대한 설명도 좋습니다. 저의 성명서는 주관적이었습니다 ("내가 만난 모든 것"). 그리고 모든 버전의 VS에 대해서는 아무런 주장도하지 않았다. –