C++内存模型和位字段的最大序列
C++ memory model and maximal sequence of bit fields
下面的例子出现在Stroustrup和CPPreference网站上:
struct S {
char a; // location #1
int b:5, // location #2
int c:11,
int :0, // note: :0 is "special"
int d:8; // location #3
struct {int ee:8;} e; // location #4
};
考虑到C++标准提供的内存位置定义:
- 标量类型的对象;
- 非零长度的最大连续位字段序列。
很明显:
- "a"是一个位置;
- "B-C"是另一个位置;
- "d"是新位置的开始。
然而,考虑到上面的定义,我不清楚为什么"d-ee"或"d-e"不是一个位置,而是两个。
引用:
- https://www.stroustrup.com/C++11FAQ.html#memory-model
- https://en.cppreference.com/w/cpp/language/memory_model
C++标准(6.7.1 intro.memory(使用极其相似的语言,甚至完全相同的示例:
。或具有非零宽度的相邻位字段的最大序列...
[ 示例:声明为
struct { char a; int b:5, c:11, :0, d:8; struct {int ee:8;} e; }
包含四个单独的内存位置:成员
a
和位字段d
和e.ee
分别是单独的内存位置...
一个区别是它使用"相邻"一词而不是"相邻"一词。
d
和ee
是连续的吗?"连续"一词的字面意思是中间没有间隙,这似乎表明它在谈论内存布局(它们之间有填充吗?但这是定义内存布局的标准的一部分,所以如果它根据这个定义事物,它将是循环的!这是一个非常糟糕的词选择,似乎是混淆的根源。
d
和ee
相邻吗?这当然是一个更好的词,因为它更明显地与代码有关,而不是与内存布局有关,但我认为您仍然可以解释它,以便在这种情况下答案是肯定或否。但鉴于有一个例子表明它们不是,我们必须接受"相邻"作为"其定义在同一结构中彼此直接相邻的字段"的简写。
首先,存在语法错误,位字段是单独的声明。
struct S {
char a; // location #1 and storage of subobject a
int b:5; // location #2, beginning of new sequence
int c:11;
int :0; // note: :0 is "special", it ends sequence of fields
int d:8; // location #3, beginning of new sequence
struct { // storage of subobject e, sequence of fields is over
int ee:8; // location #4 within e
} e;
};
字段的位置顺序由实现定义。
就C++定义而言,a
、b
、c
、d
和e
是独立的对象。但是a
、b
、c
和d
被允许在连续的位置序列中共享内存位置(物理字或字节(,因为它们是位字段,尽管e
是类类型的对象,并且必须具有唯一的内存位置。非静态成员ee
是e
的子对象,这意味着它占据了e
的一部分存储空间,所以它保证是一个单独的内存位置。
由于非唯一性,你可以获取e
的地址(operator&
(,但不能获取d
或ee
。
相关文章:
- 将结构字段的类型展开为可变模板参数
- 将位字段导出到数组
- 为了方便起见,我应该避免公开私有字段变量吗
- 当字段可以为null时,如何使用C++接口在Avro中写入数据
- 在java中读取c++字节的位字段
- 链接器找不到在虚拟类 c++ 中访问的静态字段的符号
- 私有字段对象与私有继承?
- 声明没有默认构造函数的字段
- C++内存模型和位字段的最大序列
- 声明为无效的变量或字段'...' Ardunio 编译器上的错误
- 如何在QByteArray中放置和检索位字段而不会感到痛苦?
- 在结构中使用位字段并使用C++从内存中读取实例
- 为什么使用最大位字段序列定义C++内存?
- 是否必须在内存中"next to each other"两个相邻声明的公共字段?
- 使2个非静态字段(即动态数组)相互接近使用内存
- 公用和专用字段的内存分配-GCC方式
- 使用位字段保存内存
- 构造函数中的字段初始化会损坏内存
- 删除内存字段(数组)中的单个字节
- 将内存数据PTR映射到qt输入字段