为什么 C 程序中的垃圾值有某种模式?
我在 CS50 第 4 周的记忆中尝试过这个程序。我注意到垃圾值有一个模式。最初,我认为垃圾值应该是随机的。但是,看起来根据请求的垃圾值的数量有不同的模式。
代码:
#include <stdio.h>
#include <stdlib.h>
int main (void)
{
//Create an array of 3
int scores[3];
//Print 3 random garbage values
//scores[0] have big random values
//scores[1] have 3276X
//scores[2] have 0
for (int i = 0; i < 3; i++)
{
printf("%i\n", scores[i]);
}
}
结果:
pset4/W4.1/ $ ./garbage
-1498813296
32767
0
pset4/W4.1/ $ ./garbage
-1011161520
32764
0
pset4/W4.1/ $ ./garbage
1340521040
32765
0
pset4/W4.1/ $ ./garbage
1244491248
32765
0
pset4/W4.1/ $ ./garbage
-1200874656
32764
0
任何人都可以帮助解释这里发生了什么吗?谢谢!
I try this program in CS50 Week 4 memory. I noticed there is a pattern on the garbage values. Initially, I thought garbage values should be randomize. But, it looks like there is different pattern depended on the number of garbage value requested.
Code:
#include <stdio.h>
#include <stdlib.h>
int main (void)
{
//Create an array of 3
int scores[3];
//Print 3 random garbage values
//scores[0] have big random values
//scores[1] have 3276X
//scores[2] have 0
for (int i = 0; i < 3; i++)
{
printf("%i\n", scores[i]);
}
}
Result:
pset4/W4.1/ $ ./garbage
-1498813296
32767
0
pset4/W4.1/ $ ./garbage
-1011161520
32764
0
pset4/W4.1/ $ ./garbage
1340521040
32765
0
pset4/W4.1/ $ ./garbage
1244491248
32765
0
pset4/W4.1/ $ ./garbage
-1200874656
32764
0
Can anyone help to explain what is happening here? Thanks!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
假设 x86_64,当您声明这样的数组时,编译器只是在堆栈上腾出空间,如下所示:
sub $12, %rsp
(3 个整数 12 个字节)然后当您访问该数组时,您将实际上正在查看堆栈。我知道您有 64 位操作系统,因为如果您采用
scores[0] + Scores[1] << 32
你会得到类似于0x0000 7FFC 4A2D 6DF0
的内容,而堆栈恰好从0x0000 7FFF FFFF FFFF
开始并向下增长。所以你看到的是堆栈上的指针(可能是上一次调用的返回地址),并且你知道堆栈上下一个值的底部 32 位是 0,可能是函数的局部变量,谁知道呢。重要的是堆栈不会改变那么多(特别是在 32 个高位),这就是为什么您会注意到 32 764 (0x7FFC) 这种模式。
阅读更多:
https://en.wikipedia.org/wiki/X86_calling_conventions
Assuming x86_64, when you declare an array like that, the compiler simply makes room on the stack, something like:
sub $12, %rsp
(12 bytes for 3 integers)Then when you access the array you're actually looking at the stack. I know you have a 64 bit OS because if you take
scores[0] + scores[1] << 32
you get something similar to0x0000 7FFC 4A2D 6DF0
and it just so happens that the stack starts around0x0000 7FFF FFFF FFFF
and growing down. So what your looking at is a pointer on the stack (probably a return address from a previous call) and you know that the bottom 32 bits of the next values on the stack is 0, maybe a local variable of the function, who knows.The important part is that the stack won't change that much (especially in the 32 upper bits) and this is why you're noticing this pattern of 32 764 (0x7FFC).
Read more:
https://en.wikipedia.org/wiki/X86_calling_conventions