MSVC와 GCC의 람다가 operator()
을 구현하는 펑터라는 것을 알았습니다. 포인터를 기능시키기 위해 펑터를 선호하는 이유는 무엇입니까?왜 함수 포인터가 아닌 펑터로 C++ 람다가 구현 되었습니까?
답변
문제는 C++의 람다 함수가 각 인스턴스에 대해 전달되어야하는 추가 상태 (캡처 된 변수 일명 컨텍스트)를 가질 수 있다는 점입니다 (동일한 람다 함수의 핸들 인스턴스마다 다를 수 있음).
함수는 전달한 핸들에 결합 된 상태를 가질 수 없습니다. 함수 포인터에 이런 상태를 추가하면 괄호 구문 (operator()
)을 사용하여 호출 할 수있는 래퍼를 작성하게됩니다.
람다 없이 캡쳐를 함수 포인터로 변환 할 수 있다는 사실은 주목할만한 사실입니다. 이는 이 아니기 때문에에 추가 공간이 필요하기 때문에 가능합니다.
나는 유효 기간이 클로저 인스턴스와 동일한 함수 포인터에 * 캡쳐 * 람다 변환을 추가하라는 제안을 읽었습니다. 실제로는 대부분의 아키텍처에서 기계어 명령어와 람다에 대한 포인터를 포함하는 데이터를 작성한 다음이를 실행 가능으로 표시 한 다음 런타임에 방금 작성한 함수에 대한 포인터를 리턴함으로써 가능합니다. 나는 그 제안의 상태가 무엇인지 전혀 모른다. – Yakk
@Yakk 또는 단순히 전역 변수를 사용 하시겠습니까? ;) (사실, 그 이유는 내 대답의 편집에 첫 번째 단락의 마지막 부분을 추가 한 이유입니다.) – leemes
캡처 된 상태가 다른 람다의 여러 인스턴스가 작동하지 않습니다. 기본적으로 많은 플랫폼에서 우리는 그들이 가리키는 코드에 저장된 상태로 함수 포인터를 생성 할 수 있으며'void *, void (* func) (void *)'상태 저장 콜백을 제공하지 않는 수많은 레거시 API가 있습니다 쌍. – Yakk
함수에는 상태가 없으므로 lambdas에서 요구하는 기능을 구현할 수 없습니다.
또한 람다가 고유 한 유형을 가지고 있음을 보증합니다.이 람다는 함수만으로는 실제로 할 수 없습니다.
이미 언급 한 캡쳐 기능 외에도 성능 또한 이유입니다. 일반적으로 함수 포인터는 인라인 될 수 없습니다. 펑터가 될 수 있습니다. 이것이 std :: sort가 qsort보다 빠릅니다. 앞서 언급했듯이 캡쳐가없는 람다는 함수 포인터로 바뀔 수 있지만 대부분이 오래된 API와 상호 작용합니다. 즉 낡은 win32 API 함수에 람다를 건네 줄 수가 있습니다. 일반적으로 단순한 람다 (lambda)의 경우 컴파일러는 대신 인라인을 선호합니다.
- 1. C++ 포인터가 아닌 함수 포인터
- 2. 왜 포인터가 변경 되었습니까?
- 3. 왜 C++에서 함수 포인터가 될까요?
- 4. 부패한 람다가 저장하는 함수는 어디에 있습니까? 어떻게 해방 되었습니까?
- 5. C++ - 언제 포인터가 아닌 클래스 멤버가 파괴 되었습니까?
- 6. 왜 win32/Standard 라이브러리 함수 매개 변수가 항상 포인터가 아닌 참조로 전달 되었습니까?
- 7. 왜 'is'가 'as'로 구현 되었습니까?
- 8. Py_InitModule은 함수 포인터가 아닌 이름을 복사합니까?
- 9. 함수 포인터가 멤버 함수
- 10. 거기에 함수 포인터가 C#입니까?
- 11. 포인터가 아닌 형식의 템플릿 인수
- 12. 함수 포인터가 아니라면 무엇입니까?
- 13. C++의 "this"포인터가 포인터가 아니고 참조가 아닌 이유는 무엇입니까?
- 14. 왜 프로그래머는 Symbian C++가 아닌 Nokia Qt로 전환 되었습니까?
- 15. 왜 많은 OpenCL 예제가 C++이 아닌 C로 작성 되었습니까?
- 16. 왜 AsObservable과 AsEnumerable은 다르게 구현 되었습니까?
- 17. 파이썬의 subprocess.call이 왜 이렇게 구현 되었습니까?
- 18. ConcurrentNavigableMap이 왜 건너 뛰기 목록으로 구현 되었습니까?
- 19. 왜 포인터에 대한 포인터가 매트릭스입니까?
- 20. C++ 포인터가 숫자가 아닌 메모리 주소를 인쇄합니다.
- 21. 함수 포인터가 스레드로부터 안전합니까?
- 22. DFT 함수 구현 C
- 23. stuff 함수 구현 C#
- 24. 왜 data.table이 정의 되었습니까? = 오버로드가 아닌 <-?
- 25. 왜 @ 필수가 필드가 아닌 setter로 설정 되었습니까?
- 26. 함수 포인터가 인터프리터
- 27. SplFixedArray가 C/C++에서 구현 되었습니까?
- 28. Linq 텍스트 값으로 필터링, 람다가 아닌
- 29. 왜 포인터 멤버가 0이 아닌 값으로 초기화 되었습니까?
- 30. 왜 포인터가 증가하지 않는가
표준에 그렇게 나와 있으니? 캡처 공간도 필요합니다. – chris