2

我有以下取自现代 C++ 设计的代码。当我使用它时,我得到了编译错误,我认为无效的 sizeof 操作数。任何人都可以指出是什么问题。谢谢!

template<bool>
struct CompileTimeChecker {
    CompileTimeChecker(...);
};

template<>
struct CompileTimeChecker<false> {
};

#define STATIC_CHECK(expr, msg) \
{\
class ERROR_##msg {}; \
(void)sizeof(CompileTimeChecker<(expr) != 0>((ERROR_##msg())));\
}

template <class To, class From>
To safe_reinterpret_cast(From from) {
    STATIC_CHECK(sizeof(From) <= sizeof(To), Destination_Type_Too_Narrow);
    return reinterpret_cast<To>(from);
}

int main(void)
{
    int a[20];
    void* somePointer = a;
    char c = safe_reinterpret_cast<int>(somePointer);
}

错误:

d:\technical\c++study\readparsing\readparsing\addressconv.cpp(29) : 错误 C2066: 转换为函数类型是非法的 1> d:\technical\c++study\readparsing\readparsing\addressconv.cpp( 37) : 请参阅正在编译的函数模板实例化 'To safe_reinterpret_cast(From)' 1> 使用 1> [ 1> To=int, 1> From=void * 1> ] 1>d:\technical\c++study \readparsing\readparsing\addressconv.cpp(29) : 错误 C2070: 'CompileTimeChecker<__formal> (safe_reinterpret_cast::ERROR_Destination_Type_Too_Narrow (__cdecl *)(void))': 非法 sizeof 操作数 1> with 1> [ 1> __formal=true 1 > ]

4

2 回答 2

4

最令人烦恼的解析的又一次罢工......

sizeof(CompileTimeChecker<(expr) != 0>((ERROR_##msg()))

是相同的

class Foo {};
class Bar {};
sizeof(Foo((Var()));

并且由于 Foo(Var) 可以被解释为一种类型(函数接受一个(没有参数的函数返回一个 Var)并返回一个 Foo),它就是这样。

于 2011-02-27T10:46:36.400 回答
1

就像 AProgrammer 指出的那样, (void)sizeof 并没有被编译器吞噬。我建议从 sizeof 中删除括号,如下所示:

(void)sizeof CompileTimeChecker<(expr) != 0>((ERROR_##msg()));\

这似乎让 g++ 接受它,并按照它可能的意思解释它。

如果 (void)sizeof 一直给您带来麻烦,您也可以在没有它的情况下获得静态检查功能,例如通过初始化 CompileTimeChecker 变量:

CompileTimeChecker<(expr) != 0> a((ERROR_##msg()));\
于 2011-02-27T11:50:55.737 回答