gpt4 book ai didi

c++ - 为什么在堆栈中我的函数局部变量之间有内存空间?

转载 作者:塔克拉玛干 更新时间:2023-11-03 01:17:05 27 4
gpt4 key购买 nike

我有一个在 Ubuntu x86 上用 gcc 编译的 C 程序。这是我从 main

调用的函数
void addme()
{
long a = 5;
char c = '3';
long array[3];
array[0] = 2;
array[1] = 4;
array[2] = 8;
}

如果我在最后一行中断,然后调试/检查这就是我得到的

(gdb) print &a
$5 = (long *) 0xbffff04c
(gdb) print &c
$6 = 0xbffff04b "3\005"
(gdb) print &array
$7 = (long (*)[3]) 0xbffff03c
(gdb) x 0xbffff03c
0xbffff03c: 0x00000002
(gdb) x 0xbffff040
0xbffff040: 0x00000004
(gdb) x 0xbffff044
0xbffff044: 0x00000008
(gdb) x 0xbffff04c
0xbffff04c: 0x00000005

为什么 0xbffff048、0xbffff049、0xbffff04a 和 0xbffff04b 保留给 char c 而只需要 0xbffff04b 来存储一个 char?

还有这个符号 "3\005" 是什么意思?

另一方面,如果我的方法如下,则没有填充额外三个字节的存储空间

void addme()
{
long a = 5;
char c = '3';
char line[9];
char d = '4';
}

这就是这些变量的内存分配方式(跳过地址的前导部分)

a - f04c 
c - f04b
d - f04a
line - f041, f042, f043, f044, f045, f046, f047, f048, f049

也不确定为什么 d 在内存预留中被提升到 line 之上。我假设因为它没有被初始化,所以它进入了堆栈中与初始化变量不同的区域?

最佳答案

这叫做 alignment .对象与特定整数的倍数对齐(在 long 的情况下通常为 4 或 8)以便快速访问。通常,您不必太担心 C++ 中的位置,因为语言规范通常使编译器能够选择最有效(根据您的优化方向)的方式来存储对象,通常情况就是这样.

Every object type has the property called alignment requirement, which is an integer value (of type std::size_t, always a power of 2) representing the number of bytes between successive addresses at which objects of this type can be allocated. The alignment requirement of a type can be queried with alignof or std::alignment_of. The pointer alignment function std::align can be used to obtain a suitably-aligned pointer within some buffer, and std::aligned_storage can be used to obtain suitably-aligned storage.

Each object type imposes its alignment requirement on every object of that type; stricter alignment (with larger alignment requirement) can be requested using alignas.

In order to satisfy alignment requirements of all non-static members of a class, padding may be inserted after some of its members.

(cppreference)


关于你的第二个问题,@prl给出答案:

Because c is a char, &c is a char *, so gdb prints it as a string. The first character of the string is '3', the value of c. The next character is 5, the low byte of a, which gdb prints in octal escape notation. Escape sequences in C on Wikipedia – prl 1024 min ago


为什么在 char 之后声明 char 时 pad 消失了?因为在这种情况下,char 的对齐方式显示为 1,这意味着不需要填充。另一方面,long 似乎是 4,因此必须有一个 4 字节的空间,其中放置 char

I assume because it wasn't initialized, it goes to a different region in stack than initialized variables?

不是真的。一个变量是否被初始化(通常)并不影响它的位置,只是它有一个不确定的值。另一方面,编译器可以自由地将对象按照自己喜欢的方式放置在内存中。在实践中,编译器“喜欢”在内存和时间上带来效率的实现。

关于c++ - 为什么在堆栈中我的函数局部变量之间有内存空间?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54453306/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com