[英]Writing a generalized wrapper for different functions with variable number of arguments
我想为一堆函数编写C ++包装器,这些函数在功能上都相似。 但他们都有不同数量的参数。 例如(假设typeA,typeB等是不同的typedef类型):
typeA func1 (typeB b, typeC c);
typeA func2 (typeB b, typeD d, typeE e);
这些是我要为其编写包装器的函数(注意,它们都具有返回类型typeA和类型typeB的第一个参数)。 因此,我打算创建一个通用包装器类,并将参数列表存储在构造函数中。 我希望能够在下面调用类似于“ func”的函数:
class wrapper {
public:
wrapper (/*args - a list of arguments, including
a pointer to the actual function, and
the remaining arguments depending
on the function. */);
void func (typeB b, typeA &a);
}
因此,我想以这样一种方式编写func:它使用传入构造函数的参数调用任何函数(func1或func2)。
我想知道是否可以将func1或func2视为具有可变数量的参数。 或者至少,如果在C ++中有一种方法,我可以输入一个函数和一个参数列表并获取eval(函数,argument_list)。
另一种方法是为每个函数编写一个包装器,我想避免但并不反对。 (此外,我不介意解决方案是否涉及到我不是使用包装器类而是包装器函数)
这是我在C语言中完成的操作,以包装所有功能。 我希望它能帮助/启发您。 主要限制是只能包装用户定义的函数,因为您必须修改函数的签名。
我的解决方案使用va_arg结构。
#include <stdarg.h>
void * super_wrapper( void * (*fn)(), void * ret, int n, ...)
{
va_list = my_list;
va_start(my_list, n);
ret = (*fn)(ret, n, my_list);
va_end(my_list);
return ret
}
包装器的签名使用指向您要执行的函数的指针,赋予该函数的指针以检索您的返回值,调用该函数的参数数量,然后是您想要执行的函数的参数呼叫。
va_list是参数列表。 您可以使用va_start对其进行初始化。 va_start的第一个参数是要初始化的va_list。 第二个参数是当前函数的最后一个已知参数(在本例中为“ n”)。
现在,您将放置参数va_list而不是用户定义函数中的省略号。
我有两个例子:
double sum (int n, ...)
{
int i;
double res = 0;
double tmp;
va_list = my_list;
va_start(my_list, n);
for(i=0; i<n; i++)
{
tmp = va_arg(my_list, double);
res += tmp;
}
va_end(my_list);
return res;
}
void my_print(int n, ...)
{
int i;
va_list my_list;
va_start(my_list, n);
char * tmp;
for(i=0; i<n; i++)
{
tmp = va_arg(my_list, char *);
printf("%s ", tmp);
}
printf("\n");
va_end(my_list);
}
我设法使用相同的包装器来调用这两个不同的函数,并对签名和函数主体进行了一些修改。 关键是在参数和返回中,我只给出指针。 因此,我必须取消引用指针。
void * sum (void * ret, int n, va_list my_list)
{
int i;
double res = 0;
double *tmp;
for(i=0; i<n; i++)
{
tmp = va_arg(my_list, double);
res += *tmp;
}
ret = &res;
return ret;
}
void* my_print(int n, ...)
{
int i;
char ** tmp;
for(i=0; i<n; i++)
{
tmp = va_arg(my_list, char **);
printf("%s ", *tmp);
}
printf("\n");
return ret;
}
现在,我可以在主程序中使用相同的包装器函数来调用这两个函数:
void main()
{
double two = 2.0;
double three = 3.0;
double fifteen = 15.0;
char *I, *am, *a, *great, *wrapper;
I = malloc(sizeof(char) * 2);
am = malloc(sizeof(char) * 3);
a = malloc(sizeof(char)*2);
great = malloc(sizeof(char) * 6;
wrapper = malloc(sizeof(char) * 8);
I = strcpy(I, "I\0");
am = strcpy(am, "am\0");
a = strcpy(a,"a\0");
great = strcpy(great, "great\0");
wrapper = strcpy(wrapper, "wrapper\0");
void * ret;
printf("Sum = %f\n", *( (double*)super_wrapper(sum, ret, 3, &two, &three, &fifteen) ) );
super_wrapper(my_print, ret, 5, &I, &am, &a, &great, &wrapper);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.