技术上对象可以占用非连续的存储字节吗?

bol*_*lov 4 c++ layout language-lawyer

在回答这个问题时,我被要求提供标准报价.我很震惊地在C++ 14草案中找到:

§3.9类型[basic.types]

  1. 类型为T的对象的对象表示是由类型T的对象占用的N个无符号字符对象的序列,其中N等于sizeof(T)

嗯..它并没有说"unsigned char objects"在内存中必须是连续的.也许是"序列"暗示的.然后我发现了一个特别提到的"连续存储字节",但......

§1.8C++对象模型[intro.object]

  1. [...]平凡可复制或标准布局类型(3.9)的对象应占用连续的存储字节.

什么?只需要简单的可复制和标准布局类型来占用连续的存储字节?其余的类型可以在它们占用的存储空间中有"漏洞"吗?我搜索了标准的其余部分,但找不到与"连续存储"有任何其他相关性.当然,我对标准并不熟悉.

如果这是真的(对我而言,这将是对标准的最大冲击)它是如何sizeof与指针算术?是否真的有任何架构/编译器使用(使用过的)非连续字节存储类型?

我真的希望我误解和/或遗漏一些东西.


编辑:我认为这可能与填充有关,但这种解释只有在可复制或标准布局类型无法填充的情况下才有意义.然后你说这些类型占用连续的字节存储,对于其他可以填充的类型你不会这么说.但显然不是这种情况,因为任何结构类型都可以有填充.

120*_*arm 5

具有虚拟基类的类可能不在连续的内存字节中(因为虚拟基类和类的其余部分之间的一些字节可以被也从虚拟基础派生的另一个类占用.

class A {
    int a;
};

class B: virtual A {
    int b;
};

class C: virtual A {
    int c;
};

class D: public B, C {
    int D;
}
Run Code Online (Sandbox Code Playgroud)

D类对象的内存可以这样组织:

-------
|  a  |
-------
|  b  |
-------
|  c  |
-------
|  d  |
-------
Run Code Online (Sandbox Code Playgroud)

增加记忆顺序.由"a"和"c"组成的对象"C"不占用连续的存储位置.