static_assert和constexpr到底是什么

2023-06-19 16:07:58
标签: permissive constexpr static_assert

项目中遇到一个情况,当使用find_package去引用Qt以后,编译失败了。

原因是Qt那会自动引入/permissive选项。编译时,有没有这个选项,会造成结果不同。

代码如下:

template static constexpr AVKTypeTag of()

{

if constexpr (std::is_same_v)

{

return {ID::nil};

}

else if constexpr (std::is_same_v)

{

return {ID::f32};

}

.....

else

{

#ifdef __APPLE__

#else

static_assert(false, "invalid type");

#endif

}

}

constexpr本意是用来在编译时决定表达式的值,然后编译的时候就知道是用的哪个分支,在优化时,可以直接生成对应的代码。

但是并不是编译时,选择性编译,也就是说if里的表达式是真,并不代表不再编译else分支。

而上面代码明显是写成了这个意图,搞混了编译时和运行时。static_assert(false)

这种代码永远是错的。

那为撒去掉了苹果,在Windows上有时候能正确呢?

经测试,主要目前这个方法是在Template里,当/permissive有和没有时,会导致检查一致性区别。

没有/permissive时,这个模板没引用,编译完这代码(没语法错)过了,没有实际类型导致实例化模板。能过

有/permissive时,这个模板没引用,编译完这代码(没语法错)过了,但是一致性检查可能会导致进行实例化,编译错。

同样的,如果这个模板有引用的话,就算没有/permissive,一样会报错。

也就是证明了,permissive只是在模板情况下,碰巧隐藏了错误,但是这个代码100%是错的。

也就是说编译的语法分析是正确的,语义分析是错的,不同情况可能造成了根本没有进行语义分析。


阅读(0) 收藏(0) 转载(0) 举报/Report
相关阅读

新浪BLOG意见反馈留言板 欢迎批评指正

新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 产品答疑

新浪公司 版权所有