我有两个功能稍有不同的功能,所以我不能将它们作为模板功能。
int func64(__int64 a) {
return (int) a/2;
}
int func32(int a) {
return a--;
}
根据变量b64,我想调用func64或func32。我不想在我的代码中多次检查b64是否为真,所以我使用函数指针。
void do_func(bool b64) {
typedef int (*pfunc32)(int);
typedef int (*pfunc64)(__int64);
pfunc32 call_func;
if (b64)
call_func = func64; //error C2440: '=' : cannot convert from 'int (__cdecl *)(__int64)' to 'pfunc32'
else
call_func = func32;
//...
call_func(6);
}
如何避免此错误并将call_func强制转换为pfunc32或pfunc64?
答案 0 :(得分:2)
传递一个void指针并将其强制转换为函数体。
当然,如果您使用错误的类型,这意味着更少的编译器控制;如果您致电func64
并向其传递int
,程序将编译并生成错误的结果,而不会向您提供任何错误提示。
int func64(void *a) {
__int64 b = *((__int64*) a);
return (int) b/2;
}
int func32(void *a) {
int b = *((int *) a)
return b-1;
}
答案 1 :(得分:2)
该语言要求通过相同函数指针调用的所有函数具有相同的原型。
根据您想要实现的目标,您可以使用已经提到的指针/强制转换方法(在失去类型安全性时满足此要求)或传递工会:
union u32_64
{
__int64 i64;
int i32;
};
int func64(union u32_64 a) {
return (int) a.i64/2;
}
int func32(union u32_64 a) {
return --a.i32;
}
void do_func(bool b64) {
typedef int (*pfunc)(union u32_64);
pfunc call_func;
if (b64)
call_func = func64;
else
call_func = func32;
//...
union u32_64 u = { .i64 = 6 };
call_func(u);
}
答案 2 :(得分:0)
首先,请注意函数func32
正在返回输入参数。
这是因为使用return a--
,您会在递减之前返回a
的值。
也许您的意思是return a-1
?
无论如何,您只需将此功能声明为int func32(__int64 a)
。
这样,它将具有与函数func64
相同的原型,但将与以前完全一样。
if
/ else
条件语句更好...
答案 3 :(得分:0)
我需要根据标志b64
调用func32()或func64()
这样做:
void do_func(bool b64) {
if (b64)
func64(6);
else
func32(6);
}
答案 4 :(得分:0)
为func64
制作包装:
int func64_as_32(int a) {
return func64(a);
}
现在,您可以将func32
或func64_as_32
分配给call_func
,因为它们具有相同的签名。您传入的值6
的类型为int
,因此将其传递给func64_as_32
与将其直接传递给func64
具有相同的效果。
如果您的呼叫网站传递了__int64
类型的值,那么您可以反过来执行此操作,包裹func32
。
答案 5 :(得分:0)
bool
中的C++
转换为int
(true
=> 1
,false
=> 0
)您可以使用b64
作为数组索引。因此,请参考SJuan76的建议,将函数原型转换为int f(void*)
并将它们放入数组int (*array_fun[2])(void* x);
。你可以这样调用这些函数:
int p = 6;
array_fun[b64](&p);