C++ 豆荚中的静电干扰会破坏豆荚吗?

C++ 豆荚中的静电干扰会破坏豆荚吗?,c++,types,assert,static-assert,C++,Types,Assert,Static Assert,我只是想知道。。。假设C++中有一个POD结构。如果我在里面放一个static\u assert,它会毁掉它是一个豆荚的事实吗 我知道我可以很容易地把它放在其他地方,我只是问,因为我有兴趣,如果我应该或不应该这样做 换句话说(更具体): #包括 #包括 结构A { 无效*ptr; 静态_断言(sizeof(void*)==8,“指针大小应为8;不支持平台”); }; int main() { //是否可以保证这将评估为“真”? 在C++11中,如果类型是 (标量类型、具有普通默认构造函数的普通

我只是想知道。。。假设C++中有一个POD结构。如果我在里面放一个
static\u assert
,它会毁掉它是一个豆荚的事实吗

我知道我可以很容易地把它放在其他地方,我只是问,因为我有兴趣,如果我应该或不应该这样做

换句话说(更具体):

#包括
#包括
结构A
{
无效*ptr;
静态_断言(sizeof(void*)==8,“指针大小应为8;不支持平台”);
};
int main()
{
//是否可以保证这将评估为“真”?
在C++11中,如果类型是

  • (标量类型、具有普通默认构造函数的普通可复制类或此类类型/类的数组)
  • (没有虚拟函数、虚拟基类等)
基本上没有任何东西会妨碍复制对象,就好像它们只是由原始字节组成一样

它们在编译时验证某些东西,不会改变对象的布局,也不会改变对象在构造、复制等过程中的琐碎性(或缺乏琐碎性)。因此,向类型(结构/类)添加任何数量的静态断言都不会改变它的稳定性

您可以使用
std::is\u POD::value
检查编译器是否将类型视为POD。在向其添加
static\u assert
s之前和之后,这不会改变

这是标准中关于静态断言的全部内容。来自[dcl.dcl]

在静态断言声明中,常量表达式应为可在上下文中转换为
bool
的常量表达式。如果转换后表达式的值为true,则声明无效。否则,程序格式不正确,产生的诊断消息(1.4)应包括字符串文字的文本,但基本源字符集(2.3)以外的字符不需要出现在诊断消息中


我不相信,
static\u assert
会在编译时启动,我甚至不认为它会包含在生成的二进制文件中。我身边没有得到准确答案的标准。我猜
std::is\u pod
不会真的错。@DavidHaim肯定,这就是
static\u assert
的要点。不过,它还没有定义如何导入删除它-因此,如果它将生成一个虚拟成员来执行其工作,理论上它可能会破坏
is_pod
(我不明白它为什么会这样做-但这是另一个故事…)对吗?@atlaste编译时静态断言将由编译器计算,而不是运行时由编译代码的二进制文件计算。因此,没有代码(虚拟或其他)理想情况下,应该为
static\u assert
生成,否则将
static\u assert
视为运行时
assert
,这将是一个低效的实现。请注意,如果您想消除任何微小的可能性,没有什么可以阻止您将
static\u assert
引入全局命名空间至少,它可能不会像预期的那样起作用(正如@legends2k也指出的那样,不应该真的起作用)。当然,这两个函数都是在编译时进行计算的,但afaik在std中都没有禁止它们添加虚拟函数的实现约束,从而违反了POD约束,对吗?次要部分有一个约束,即类不应该有任何虚拟函数。如果它不是次要的,它就不是POD。@atlaste:I我不记得有明确的禁令(这需要检查整个标准),但我相信有一个广泛的共识,即编译器不能仅仅因为喜欢就添加虚拟函数。根据标准添加虚拟函数的唯一方法是声明一个或继承一个。(注意,共识是这是一个详尽的列表)@MSalters好的,那么更可能的情况是它将生成一个非POD结构的helper变量如何。(例如,使用模板专门化,您可以根据条件创建一个“断言”结构)我的意思是,这是一个愚蠢的实现,因为你可以使用TyPufF,但是我想它是允许的,对吗?@ ATLASTE:现在这是一个公平的观点。你不能通过内省(不是C++特性)找到那个成员,并且你无法区分它与填充(因为编译器几乎可以自由地添加它)。。编译器可能会选择一个不会与您的成员冲突的名称(例如,
\u a
)。这里的想法可能是,生成的helper变量在源代码中没有声明。这与我在上面为虚拟函数提出的逻辑大致相同。如果成员必须具有由其声明引入的属性,则成员不能是隐式的。
#include <iostream>
#include <type_traits>

struct A 
{
    void* ptr;

    static_assert(sizeof(void*) == 8, "Pointer should have size 8; platform unsupported");
};

int main()
{
    // Is it guaranteed that this will evaluate to 'true'?
    std::cout << std::is_pod<A>::value << std::endl;
}