Closed. This question needs to be more focused。它当前不接受答案。












想改善这个问题吗?更新问题,使其仅关注editing this post的一个问题。

4年前关闭。



Improve this question




我最近发布了一个有关unaligned memory access的问题,但是给出了答案,我有点迷失了。我经常听到“对齐内存访问比未对齐访问有效得多”,但实际上我不确定什么是未对齐内存。所以:
  • 什么是未对齐内存?
  • 如何声明C++中未对齐的内容? (小示例程序)
  • 如何访问和处理C++中未对齐的内容? (小示例程序)
  • 是否有一种方法可以使用已定义的行为方法来处理未对齐的内存,或者所有这些都是C++中与平台有关的/未定义的行为?
  • 最佳答案

    某些内容是否未对齐取决于数据类型及其大小,如Gregg的回答所解释。

    编写良好的程序通常不具有未对齐的内存访问权限,除非编译器引入了该访问权限。 (是的,在矢量化过程中会发生,但是我们跳过它)。

    但是您可以用C++编写程序来强制进行未对齐的内存访问。下面的代码就是这样做的。

    #include <iostream>
    using namespace std;
    int main() {
    
      int a[3] {1, 2, 3};
    
      cout << *((long long *)(&a[0])) << endl;
      cout << *((long long *)(&a[1])) << endl;
    
      cout <<  (long long) (&a[0]) << endl;
      cout << (long long) (&a[1]) << endl;
    
      return 0;
    
    }
    

    代码的输出是这个
    8589934593
    12884901890
    70367819479584
    70367819479588
    

    该程序做什么?
    我声明了一个大小为3的整数数组。该数组将对齐4字节,因为int是4字节数据类型(至少在我的平台上)。因此,a [0]的地址可被4整除。现在,a [0]和a [1]的地址都可被4整除,但只有其中一个的地址可被8整除。

    因此,如果我将a [0]和a [1]的地址强制转换为long long指针(在我的平台上为8字节数据类型),然后再引用这两个指针,则其中之一将是未对齐的内存访问。这不是未定义的行为AFAIK,但是它将比对齐的内存访问慢。

    如您所见,此代码包含C样式强制转换,这不是一个好习惯。但是我认为可以强制执行一些奇怪的行为。

    让我知道您是否对代码输出有疑问。您应该了解整数的字节序和表示法,才能理解前两行。第三和第四行是整数数组的前两个元素的地址。那应该更容易理解。

    关于c++ - 在C++中声明,操作和访问未对齐的内存,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/39922500/

    10-12 14:51
    查看更多