매크로 "Higher Order Function" 생성기를 사용한 C의 기능 프로그래밍
이건 정말 대단한 질문이니 주의를 기울이세요 ;-)
컴파일러 정적 타입 검사를 유지하면서 C에서 일반적인 수집 동작(검색, 각각에 대한 등)에 템플릿 함수를 사용하고 싶습니다.이 예제와 같이 간단한 콜백을 사용할 때는 매우 간단합니다.
#define MAKE_FOREACH(TYPE)\
void foreach_##TYPE (TYPE[n] array, int n, void(*f)(TYPE)) {\
for(int i = 0; i < n; i++) {\
f(array[i]);\
}\
}
다음과 같은 작업을 수행할 수 있습니다.
MAKE_FOREACH(int)
MAKE_FOREACH(float)
void intcallback(int x){
printf("got %d\n", x);
}
void floatcallback(float x){
printf("got %f\n", x);
}
int main(){
int[5] iarray = {1,2,3,4,5};
float[5] farray = {1.0,2.0,3.0,4.0,5.0};
foreach_int(iarray, 5, intcallback);
foreach_float(farray, 5, floatcallback);
}
반환 유형을 사용하여 콜백을 구현하고 싶다면, 예를 들어 "지도" 기능을 만들 수 있습니다.
#define MAKE_MAP(TYPE, RTYPE)\
RTYPE* map_##TYPE (TYPE[n] array, int n, RTYPE(*f)(TYPE)) {\
RTYPE* result = (RTYPE*)malloc(sizeof(RTYPE)*n);\
for(int i = 0; i < n; i++) {\
result[i]=f(array[i]);\
}\
}
지금까지, 좋아요.문제는 콜백 함수가 입력된 인수의 수를 모두 허용하기를 원하는 시점에 발생합니다.
아이디어는 다음과 같습니다.
#define MAKE_MAP(TYPE, RTYPE, ...)\
RTYPE* map_##TYPE (TYPE[n] array, int n, RTYPE(*f)(TYPE, __VA_ARGS__), __VA_ARGS__)
/*this would work for the declaration (because just the types would be enough)
but the parameter names are missing :-s*/ \
{\
RTYPE* result = (RTYPE*)malloc(sizeof(RTYPE)*n);\
for(int i = 0; i < n; i++) {\
result[i]=f(array[i], /*here the names of the parameters, in order*/);\
}\
}
보다시피 지도 함수를 다음과 같이 선언할 수 있습니다.
MAKE_MAP(int, float, char)
제공:
float* map_int(int[n] array, int n, float(*f)(int, char), char);
하지만 저는 preprocessor로 전달되는 parameter passing을 어떻게 구현할 것인지 알 수가 없습니다.여기서 여러분의 도움과 아이디어, 제안을 부탁드립니다.
(그런데, va_list 인수를 콜백에 전달하고 템플릿으로 va_list 인수를 사용하라고 말하지 마세요. 왜냐하면 이 모든 것은 유형 확인 때문이었으니까요 :-p)
Linux/B를 사용하는 경우SD 유닉스, 큐(3)를 보고 확인합니다./usr/include/sys/queue.h
- 전에 해본적이 있습니다 :)
최근의 한 질문은 도서관들을 학대하는 뻔뻔한 전처리기들을 꽤 많이 제기했습니다.
참고로, GCC 4.6의 소스 코드는 벡터에 대해 유사한 트릭을 구현합니다.파일을 조사합니다.gcc/vec.h
언급URL : https://stackoverflow.com/questions/894167/functional-programming-in-c-with-macro-higher-order-function-generators
'programing' 카테고리의 다른 글
Chocolatey, OneGet, PsGet, NuGet, ...의 차이점은 무엇입니까? (0) | 2023.10.25 |
---|---|
경로를 구성하지 않고 angularjs 단일 페이지 응용 프로그램에서 페이지 새로 고침을 탐지하려면 어떻게 해야 합니까? (0) | 2023.10.25 |
목표 C: SHA1 (0) | 2023.10.25 |
파이썬 애플리케이션을 정적 바이너리로 컴파일하는 방법이 있습니까? (0) | 2023.10.25 |
동적으로 로드된 스크립트를 기다리는 중 (0) | 2023.10.25 |