记忆位置混乱

Confusion about memory positions

我一直在看一本计算机体系结构相关的书,我遇到了一个特定的情况,看看:

在计算机中,字和总线大小为32 位。假设你想在内存中存储3个变量:

a)First name initial (8 bits, char)

b)First last initial (8 bits,char)

c)ID number (32 bits, int)

提出了两种存储方式:

我脑子里闪过这个问题:

为什么 'Way B' 占用的内存位置比 'Way A' 少,因为它们都包含相同的变量?当在内存中访问变量时,这两种存储变量的方式哪种更有效?

有人可以给我解释一下吗?

这就像问为什么用机器语言编写的程序的执行速度比用高级语言编写的程序快?当你在位级上操作信息时执行或访问该信息的速度更快。因此,当您以 Way A 存储信息时,它将分别对每个变量(Fname、Id、Lname)使用 1 word(not 1 Byte)。但是在方式B中,你所做的被称为数据打包。您将 Fname 和 Lname 打包在一个内存位置,这就是访问速度比 Way A 快的原因。 如果你稍微了解一下Structures, Slack Bytes(or padding) and Bit Fields in C,你会很容易理解这一点。

查看给定的C代码:--

#include <stdio.h>

struct test
{
    char firstname;
    int id;
    char lastname;
}x;

int main()
{
    printf("Size of Struct: %d, Size of Char: %d, Size of Int: %d", sizeof(x), sizeof(char), sizeof(int));
    return 0;
}

输出:

Size of Struct: 12, Size of Char: 1, Size of Int: 4

但是我们都知道sizeof a structure总是等于其成员大小的总和,即这里应该是1+4+1 = 6但是由于char, int & char之间的填充字节这个结构,它的大小是 12 个字节。因此,在这里您正在访问比 "Way B".

额外的内存位置

注意:对于不同的成员序列或数据类型,输出可能不同。

您可以参考 here 了解有关 Padding Bytes 或数据如何存储在内存中的更多信息。 希望对你有帮助。

最小可寻址单元是32位的,有点奇怪,但不是问题。

我们来看看FIRST NAMELAST NAME在A方式中是如何存储的

 31                                         7           0
+------------------------------------------+------------+
|                  UNUSED                  | FIRST NAME |
+------------------------------------------+------------+
|                  UNUSED                  | LAST NAME  |
+------------------------------------------+------------+

只使用最低8位,不使用高24位。如果我们要保存space,显然我们最多可以在未使用的区域中放置24位信息。 B路就是这么做的。

 31                            15           7           0
+-----------------------------+------------+------------+
|            UNUSED           | LAST NAME  | FIRST NAME |
+-----------------------------+------------+------------+

方法 B 将 FIRST NAMELAST NAME 放在同一内存单元中,较少未使用 space。所以方法 B 更 space 有效。

谈到访问效率,那就是另一回事了。在方式A中,我们可以使用各自的地址访问所有三个成员。

FIRST NAME : 0000
ID         : 0001
LAST NAME  : 0002

它的等效 C 代码是:

struct S {
    char first_name;
    int id;
    char last_name;
};

但是在方式B中,FIRST NAMELAST NAME共享同一个地址,我们需要使用位操作来获取它们。

FIRST NAME : 0000 (bit 0~7)
LAST NAME  : 0000 (bit 8~15)
ID         : 0001

其等效的C代码即可(这里我不打算使用位域)。由于没有直接的方法访问这两个成员,我们需要进行如下操作:

struct S {
    short packed_name;  // assume short represents 16-bit variable here
    int id;
};

struct S s;
char first_name = s.packed_name & 0x00ff;        // get lowest 8 bits
char last_name = (s.packed_name & 0xff00) >> 8;  // get bit 8~15, then shift it right

显然方式 A 的访问效率更高,因为不需要这些位操作。