【发布时间】:2017-11-05 18:11:21
【问题描述】:
在 C++ 内置多维数组的上下文中,我很难理解 constexpr。下面的例子说明了我的问题。
a) 只要我不将它分配给任何东西,在编译时查看一个值就可以正常工作。
b) 但是如果我尝试将它分配给另一个 constexpr 变量,则会出现编译时错误。
我环顾四周,甚至检查了标准文档。任何能向我解释这一点的人都是真正的大师。 FWIW,我在启用 C++14 的 Xcode 下使用 CLang 8.1 编译它。
using uint8_t = unsigned char;
#if 1
enum class safe_numerics_error : uint8_t {
success = 0,
failure, // result is above representational maximum
error_count
};
#else
// avoiding enum class fails to solve problem
struct safe_numerics_error {
const uint8_t m_t;
constexpr const static uint8_t success = 0;
constexpr const static uint8_t failure = 1;
constexpr safe_numerics_error(uint8_t t) :
m_t(t)
{}
constexpr operator uint8_t () const {
return m_t;
}
};
#endif
template<typename R>
struct checked_result {
const safe_numerics_error m_e;
const union {
const R m_r;
char const * const m_msg;
};
constexpr /*explicit*/ checked_result(const R & r) :
m_e(safe_numerics_error::success),
m_r(r)
{}
constexpr /*explicit*/ checked_result(const safe_numerics_error & e) :
m_e(e),
m_msg("")
{}
};
// integers addition
template<class T>
constexpr inline checked_result<T> operator+(
const checked_result<T> & t,
const checked_result<T> & u
){
// "Constexpr variable 'e' must be initialized by a constant expression"
constexpr const safe_numerics_error x[2][2]{
// t == success
{
// u == ...
safe_numerics_error::success,
safe_numerics_error::failure
},
// t == positive_overflow_error,
{
// u == ...
safe_numerics_error::failure,
safe_numerics_error::failure
}
};
#if 1 // compile fails
constexpr const safe_numerics_error e = x
[static_cast<uint8_t>(t.m_e)]
[static_cast<uint8_t>(u.m_e)]
;
return
(safe_numerics_error::success == e)
? t.m_r + u.m_r
: checked_result<T>(e)
;
#else // works as expected
return
safe_numerics_error::success == x
[static_cast<uint8_t>(t.m_e)]
[static_cast<uint8_t>(u.m_e)]
? t.m_r + u.m_r
: checked_result<T>(x
[static_cast<uint8_t>(t.m_e)]
[static_cast<uint8_t>(u.m_e)]
)
;
#endif
}
int main(){
constexpr const checked_result<unsigned> i = 0;
constexpr const checked_result<unsigned> j = 0;
constexpr const checked_result<unsigned> k = i + j;
// return k.m_r;
constexpr const checked_result<unsigned> i2 = safe_numerics_error::failure;
constexpr const checked_result<unsigned> j2 = 0;
constexpr const checked_result<unsigned> k2 = i2 + j2;
return k2.m_r;
}
【问题讨论】:
-
错误是什么?在哪一行?
-
您的编译器看不到的代码(在
#else块中)只是噪音还是问题的一部分? -
对此有两个 cmets:1)在错误情况下,您在 main 末尾返回 m_r,这是无效的,因为该对象是用错误构造的 2)为什么不只是 & 枚举值而不是使用二维数组?即成功 & 成功 == 成功,但失败 & 任何东西 = 失败
-
哦,另一个:constexpr 变量本质上是 const,所以你不必重新指定。
标签: c++ arrays c++14 constexpr