以下代码在GCC上编译清理但在Clang上出错:
typedef void (MyFuncPtr)();
void foo(const MyFuncPtr* ptr)
{
MyFuncPtr* myTestPtr = ptr;
}
Clang错误:
error: cannot initialize a variable of type 'MyFuncPtr *' (aka 'void (*)()') with an lvalue of type 'const MyFuncPtr *'
(aka 'void (const *)()')
我尝试过以下解决方案,除了C风格的演员之外,他们都会遇到错误:
的const_cast:
MyFuncPtr* myTestPtr = const_cast<MyFuncPtr*>(ptr);
错误:
error: const_cast to 'MyFuncPtr *' (aka 'void (*)()'), which is not a reference, pointer-to-object, or pointer-to-data-member
reintepret_cast:
MyFuncPtr* myTestPtr = reinterpret_cast<MyFuncPtr*>(ptr);
错误:
error: reinterpret_cast from 'const MyFuncPtr *' (aka 'void (const *)()') to 'MyFuncPtr *' (aka 'void (*)()') casts away
qualifiers
C式演员:
MyFuncPtr* myTestPtr = (MyFuncPtr*) ptr;
成功!
问题:
为什么const_cast不能处理函数指针?
使用C风格的演员是唯一的解决方案吗?
为什么这个没有强制转换的GCC呢?
提前致谢!
编译器版本:
* G ++版本4.6.3
* clang版本3.5.0.210790
答案 0 :(得分:3)
在您的代码中,MyFuncPtr
是一个函数类型(不是函数指针类型)。您的代码尝试使用const MyFuncPtr
类型,它将const
应用于函数类型。
但是,根据C ++ 14 [dcl.fct] / 6中的注释,没有const限定的函数类型:
cv-qualifier-seq 在函数声明符中的作用与在函数类型之上添加cv-qualification不同。在后一种情况下,忽略cv限定符。 [注意:具有 cv-qualifier-seq 的函数类型不是cv限定类型;没有cv限定的函数类型。 - 结束记录]
本节主要讨论 cv-qualifier-seq ,它是在成员函数之后发生的限定符。但是,顺便说一下,它似乎指定一般应用于函数类型的cv限定符将被忽略。
所以你的代码应该与:
相同typedef void (MyFuncPtr)();
void foo(MyFuncPtr* ptr)
{
MyFuncPtr* myTestPtr = ptr;
}
这意味着clang会报告错误。