需要帮助理解指针算术

时间:2012-06-21 16:26:31

标签: c++ memory pointers

我在理解指针运算或分配内存方面遇到了麻烦。在下面的代码片段中,我试图访问'size = 1'的值,该值位于'test'之前的8个字节,但是我没有获得size的值,并且该值不是随机的。所以我可能在理解字节大小时遇到​​问题。如果void *,long和char是8个字节,那么在使用指针算法时是否重要?

#include <iostream>
using namespace std;

char arrayOfCrap[100];

void * what(){
    long * size ; 
    size = (long*)&arrayOfCrap[28];
    *size = 1;
    return ((void*) &arrayOfCrap[29]);
}

int main(){

    long * test;
    test =  (long*)what();
    *test = 1221;
    cout << "Value of test: " << *test << endl;
    cout << "Long number before test: " << *(test-1) << endl;
}

当main从what()的void *'指针前进时,代码有效:

#include <iostream>
using namespace std;

char arrayOfCrap[100];

void * what(){
    long * size ; 
    size = (long*)&arrayOfCrap[28];
    *size = 1;
    return ((void*) &arrayOfCrap[28]);  //change from above
}

int main(){

    long * test;
    test =  (long*)what();
    test++;                             //change from above
    *test = 1221;
    cout << "Value of test: " << *test << endl;
    cout << "Long number before test: " << *(test-1) << endl;
}

2 个答案:

答案 0 :(得分:4)

您的代码未在*size之前找到*test八个字节:

size = (long*)&arrayOfCrap[28];

arrayOfCrap是char arrayOfCrap[100]所以arrayOfCrap[28]是偏移量为28的字符,arrayOfCrap[29]是偏移量为29的字符。

test++工作的原因是测试类型为long*,因此递增它实际上会移动到下一个位置很长时间,而递增char*或使用索引char数组为您提供的下一个位置

您也可以执行以下任一操作:

void * what(){
    long * size ; 
    size = (long*)&arrayOfCrap[28];
    *size = 1;
    return size+1;
}

void * what(){
    long * size ; 
    size = (long*)&arrayOfCrap[28];
    *size = 1;
    return ((void*) &arrayOfCrap[28 + sizeof(long)];
}

顺便说一句,将指针指向任何内存位置并将其视为指向另一种类型的指针并不一定安全。某些平台要求某些类型“对齐”,或者使这些类型仅存在于某个值的倍数的地址。在那些平台上,读取或写入未对齐的对象可能会崩溃(总线错误)或以其他方式具有未定义的行为。此外,某些平台可能不会崩溃或行为不正确,但在读取/写入对齐的对象时具有更好的性能。我知道这完全不在你的实验中,但你应该知道真正的代码。这是一个不在实际代码中做什么的例子:

int read_int(char *&c) {
  int out = *(int*)c; // c may not be properly aligned!
  c += sizeof(int);

  return out;
}

不幸的是,在一个通用平台x86上,未对齐的访问通常只是缓慢而不是总会导致崩溃的东西,因此该平台的用户必须特别小心。

答案 1 :(得分:2)

当您递增指针时,它不会增加指针大小,而是增加指针类型的大小。 char*指针递增sizeof(char)long*指针递增sizeof(long)

sizeof(char *)sizeof(long *)应该是相同的大小(通常在32位系统上为4个字节,在64位系统上为8个字节)。

但是,sizeof(char)sizeof(long)不一样。

您的指针大小与整数大小混淆。

#include <iostream>
using namespace std;

int main()
{
    cout << "\n sizeof(char*)   " << sizeof(char *);
    cout << "\n sizeof(char)    " << sizeof(char);
    cout << "\n sizeof(long*)   " << sizeof(long *);
    cout << "\n sizeof(long)    " << sizeof(long);
}

在此处查看此行动:http://ideone.com/gBcjS