그래서 나는 그들이 어떻게 작동하는지 궁금해하고있었습니다. "함수 호출자"가 의미하는 바를 설명하기 위해 나는 glutTimerFunc
이라는 함수를 매개 변수로 취할 수 있으며 선언 된 것을 모른 채 호출 할 수도 있습니다. 어떻게 이러는거야?함수 호출자 (콜백)가 C입니까?
답변
당신이 말하는 것은 callback이며 C 및 C++에서는 function pointers으로 구현됩니다.
glut에 대해 언급 했으므로 freeglut 소스 코드에서 직접 실제 예를 들어 봅시다. 코드가 더 간단하기 때문에 glutTimerFunc 대신 glutIdleFunc을 사용합니다.
유휴 함수 콜백 (glutIdleFunc에 제공하는 것)은 매개 변수를 사용하지 않고 아무것도 반환하지 않는 함수에 대한 포인터입니다.
여기typedef void (* FGCBIdle)(void);
이 (유휴 FreeGlut 콜백 짧은) FGCBIdle 대가 형 공극 아니 파라미터를 취하지 않는 기능에 대한 포인터로서 정의된다 : 타입 정의는 함수 유형 이름을 지정하는 데 사용된다. 이는 식을 쉽게 작성하고 저장 영역을 할당하지 못하도록하는 형식 정의 일뿐입니다.
Freeglut에는 다양한 설정을 저장하는 SFG_State라는 구조가 있습니다. 그 구조의 정의의 일부는 다음과 같습니다
struct tagSFG_State
{
/* stuff */
FGCBIdle IdleCallback; /* The global idle callback */
/* stuff */
};
구조체는 우리가 특정 함수 포인터의 또 다른 이름 설립 형 FGCBIdle의 변수를 보유하고 있습니다. IdleCallback 필드가 glutIdleFunc 함수를 사용하여 사용자가 제공하는 함수의 주소를 가리 키도록 설정할 수 있습니다. 함수의 (단순화 된) 정의는 다음과 같습니다.
void glutIdleFunc(void (* callback)(void))
{
fgState.IdleCallback = callback;
}
여기서 fgState는 SFG_State 변수입니다. 보시다시피 glutIdleFunc는 하나의 매개 변수를 취합니다.이 매개 변수는 매개 변수를 사용하지 않고 아무 것도 반환하지 않는 함수에 대한 함수 포인터입니다.이 매개 변수의 이름은 콜백입니다. 함수 내에서 전역 fgState 변수의 IdleCallback은 사용자가 제공 한 콜백으로 설정됩니다. glutIdleFunc 함수를 호출하면 자신의 함수 이름 (예 : glutIdleFunc (myIdle))을 전달하지만 실제로 전달하는 것은 함수의 주소입니다. 유휴 콜백 공급 사용자가 사용할 수있는 경우,이 루프에서 호출
if(fgState.IdleCallback)
{
/* stuff */
fgState.IdleCallback();
}
:
나중에 위해 glutMainLoop에 의해 시작된 큰 과잉 이벤트 처리 루프 내에서, 당신은이 코드를 찾을 수 있습니다. 내 포스트 시작 부분에서 함수 포인터 자습서를 확인하면 구문을 더 잘 이해할 수 있지만 일반적인 개념이 더 이해되기를 바랍니다.
매개 변수는 함수에 대한 포인터입니다. 함수 선언이 요구 사항 (예 : 매개 변수의 수와 유형, 호출 규칙)과 일치하는지 확인하는 것은 호출자의 책임입니다.
매개 변수로 전달 된 함수는 함수 포인터로 전달됩니다.
컴파일 된 코드에서 함수는 CPU가 실행할 벡터화 할 수있는 주소에 불과합니다. 함수 포인터를 전달할 때 컴파일러 (및 나중에 링커) 올바른 주소를 호출에 삽입합니다.
함수 매개 변수는 실행 코드가 스택 (또는 아키텍처에 따라 레지스터)에 값을 밀어 넣고 반환 값을 팝 아웃 (읽기)하기를 기대하는 것과 정확하게 일치해야합니다.
- 1. Python에서 다른 함수 안에 호출자 함수 이름을 가져 오는 중입니까?
- 2. Erlang은 클러스터 컴퓨팅 세계의 C입니까?
- 3. 번역기와 전처리 기가 같은 c입니까?
- 4. C++에서 생성자 호출자 찾기
- 5. PHP : 친구 클래스 및 ungreedy 호출자 함수/클래스
- 6. 하나의 함수로 호출자/콜백 배치하기
- 7. printf ("string1" "string2")는 유효한 C입니까?
- 8. Ruby에서 호출자 모듈 얻기
- 9. 상속, 기본 클래스 호출자
- 10. 알 수없는 호출자 android
- 11. HTTP HTTP 호출자 사용법
- 12. 명령 패턴 : 클라이언트 및 호출자
- 13. 라이브러리에서 호출자 스크립트 경로를 찾으십시오.
- 14. 로깅 어플리케이션 블록 - 호출자 로깅
- 15. Android 용 전체 화면 호출자
- 16. jQuery getJSON - 호출자 함수의 반환 값
- 17. arguments.callee.caller ... 호출자 객체의 'this'참조를 얻는 방법?
- 18. NSIS 호출자 파일 경로 가져 오기
- 19. Java의 "호출자"는 Ruby의 "수신자"와 동일합니까?
- 20. 저장된 proc 또는 트리거 내의 호출자 결정
- 21. FxCop, 종속 어셈블리의 호출자 목록 구성
- 22. SQL Server에서 트리거 호출자 가져 오기
- 23. 썬더 돔 액션 호출자 asp.net mvc
- 24. Pythonize Me : 파이썬에서 호출자 컨텍스트 변수를 관리하는 방법? (Python/Django)
- 25. Javascript에서 원래 호출자 함수로 데이터를 반환하는 방법은 무엇입니까?
- 26. C++ : 함수 호출 트리 생성
- 27. WSPBuilder, 구성 저장 및 부분적으로 신뢰할 수있는 호출자
- 28. 일반 WCF 서비스 호출자 생성 - 일반, 대리인 및 람다
- 29. 호출자 함수가 XML 리더 리소스를 닫을 수 있습니다.
- 30. 메소드 또는 생성자의 호출자 인스턴스 (클래스가 아님) 검색