c - 为什么我的指针运算在这个数组中失败

标签 c arrays pointers

#include <stdio.h>
#include <stdlib.h>

// Resource
typedef struct _Resource Resource;

// ResourceBuffer
typedef struct _ResourceBuffer ResourceBuffer;
ResourceBuffer *resource_buffer_new(int);
ResourceBuffer *resourceBuffer;
void resource_buffer_test();

struct _ResourceBuffer {
    char *id;
    int size;
    Resource **buffer;
};

struct _Resource {
    int id;
    char *status;
};

Resource *resource_new(int i) {
    Resource *r = malloc(sizeof(*r));
    r->status = "groovy";
    r->id = i;
    return r;
}

void resource_buffer_test() {

    printf("buftest has buf as %d\n",resourceBuffer->buffer);
    printf("buftest has drefbuf as %d\n",*(resourceBuffer->buffer));

    Resource *bp[resourceBuffer->size];
    bp[0] = *(resourceBuffer->buffer+0);
    bp[1] = *(resourceBuffer->buffer+1); 
    bp[2] = *(resourceBuffer->buffer+2);
    int i = 0;
    for (i = 0; i < 3; i++) {
        printf("address is %d\n", bp[i]);
    }
    for (i = 0; i < 3; i++) {
        //printf("ptrBuffer r%d is %s\n", i, (*((Resource **)(resourceBuffer->buffer)+i))->status);
        printf("Buffer r%d is %s\n", bp[i]->id, bp[i]->status);
    }
}

ResourceBuffer *resource_buffer_new(int bufferSize) {
    ResourceBuffer *r = malloc(sizeof(*r));
    Resource *b[bufferSize];
    int i;
    for (i = 0; i < bufferSize; i++) {
        b[i] = resource_new(i);
    }
    for (i = 0; i < bufferSize; i++) {
        printf("res address is %d\n", b[i]);
        printf("pnt address is %d\n", &b[i]);
    }
    printf("b address is %d\n", b);
    r->buffer = b;
    printf("buffer set to %d\n", r->buffer);
    r->size = bufferSize;
    r->id = "foo";
    return r;
}

int main(int argc, char** argv) {
    // initialize buffer
    resourceBuffer = resource_buffer_new(3);
    resource_buffer_test();

    return (EXIT_SUCCESS);
}

输出为:

res address is 36585520
pnt address is 783569984
res address is 36585552
pnt address is 783569992
res address is 36585584
pnt address is 783570000
b address is 783569984
buffer set to 783569984
buftest has buf as 783569984
buftest has drefbuf as 36585520
address is 36585520
address is 36585552
address is 36585520
Buffer r0 is groovy
Buffer r1 is groovy
Buffer r0 is groovy

令我困惑的是最后 6 行...为什么在 resource_buffer_test() 中执行 b[0]b[2]最终指向资源结构 r0?

由于某种原因,这部分失败了:

bp[0] = *(resourceBuffer->buffer+0);
bp[1] = *(resourceBuffer->buffer+1); 
bp[2] = *(resourceBuffer->buffer+2);

其中 *(resourceBuffer->buffer+2) 不知何故最终指向数组中的第一个元素,而不是第三个。

为什么会发生这种情况?是什么导致 C 指针算术将 *(resourceBuffer->buffer+2) 重置回 *(resourceBuffer->buffer+0)

真正奇怪的是(无论如何对我来说)......是当我将 resource_buffer_new 函数更改为如下所示时:

ResourceBuffer *resource_buffer_new(int bufferSize) {
    ResourceBuffer *r = malloc(sizeof(*r));
    Resource *b[bufferSize+1];

(注意*b[bufferSize+1])——然后它按预期工作..

为什么我的缓冲区数组中需要有额外的空间才能使指针算术正常工作?

最佳答案

r->buffer = b; 是你的问题。 b 是一个局部变量,一旦从 resource_buffer_new() 返回,该变量就会超出范围。如果您将 b 设为静态或分配它,那就没问题了。

关于c - 为什么我的指针运算在这个数组中失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27054000/

相关文章:

c++ - c/c++ 通过指针传递参数/通过引用堆栈帧布局传递参数

c - 解释以下语法,我无法理解

c - 从标准输出写入文件

c - C语言中如何将结构体成员赋值给变量

将字符串复制到字符串数组中

c - 如何在 C 中的 for 循环中分配给变量?

c - 何时在程序中首先获取高速缓存行?

c - 递归结构(二叉树): obtain values via struct pointer from inside function

c++ - 如何将文件中的值输入到矩阵中?

javascript - 将数组返回给父函数调用