简体   繁体   English

传递给C中的函数时擦除指针数组的内容

[英]Pointer array contents wiped when passed to a function in C

so I am loading lines of floats from text files and storing them in a pointer array, before saving them back to a text file and adding a reference to their size. 因此,我先从文本文件加载浮点数行,然后将它们存储在指针数组中,然后再将它们保存回文本文件并添加对其大小的引用。 The number of values in the text file varies so the array must be dynamic. 文本文件中值的数量各不相同,因此数组必须是动态的。 I define my pointer array in main like this. 我像这样在main中定义指针数组。

size_t size = (int)100 * sizeof(float);
float * val = malloc(size);

I then pass the pointer array to a function that loads the text file and saves the values to it, like this. 然后,我将指针数组传递给加载文本文件并将其保存值的函数,如下所示。

//Read file into array.
int readFile(float *val, int size) {

char buf[20] = { 0 };
val[0] = 0;
double temp = 0;
int i = 1;
FILE *file;
file = fopen("C:\\Users\\MoldOffice\\Dropbox\\VS\\finalproj\\ecgproject\\dataStream", "r");
if (!file) {
    printf("Coulding find file.\n");
    exit(1);
}

while (fgets(buf, 20, file) != NULL) {
    temp = atof(buf);
    if (temp != 0) {
        // Increment i to find the size of the useful data.
        val[i] = temp;
        //printf("%d",val[i]);
        i++;
        if (i == size / sizeof(float)) {
            size += 100*sizeof(float);
            double* val_temp = realloc(val, size);
            if (val_temp == NULL) {
                printf("Realloc failed.\n");
            }
            else {
                val = val_temp;
            }
        }
    }
}
//Test that the array is readable.
for (int i = 0; i < 5; i++) printf("val[%d]=%f\n", i, val[i]);

return(i);
fclose(file);

This works fine and when I print the contents of the pointer array back in main, it works. 这可以正常工作,当我在main中将指针数组的内容打印回去时,它可以工作。 I then pass the same pointer array to another function which saves the array in a new text file, along with the size on the first line, the problem is that when I pass the pointer array for a second time, the contents have changed (mostly 0 with some random numbers). 然后,我将相同的指针数组传递给另一个函数,该函数将数组和第一行的大小保存在一个新的文本文件中,问题是当我第二次传递指针数组时,内容已更改(大部分是0(带有一些随机数)。 I have absolutely no idea why this is happening.. Any ideas? 我完全不知道为什么会这样。 The function that writes the file is here: 写入文件的功能在这里:

// Write file into array.
void writeFile(float *val,int size) {

printf("%d",sizeof(val));
FILE *file;
int sampleNum;
char buf[10];
file = fopen("sampleNum.txt", "r");
if (file == NULL) { sampleNum = 0; }
else { fscanf(file, "%d", &sampleNum); printf("%d",sampleNum);}
char fileString[10];
sprintf(fileString,"sample%d\0", sampleNum);
file = fopen(fileString, "w");

//Test that the array is readable.
for (int i = 0; i < 5; i++) printf("val[%d]=%f\n", i, val[i]);

//Print the array to a text file and save.
fprintf(file, "%d\n", size);
for (int i = 1; i < size; i++) {
    fprintf(file, "%f\n", val[i]); 
    printf("%f\n", val[i]); }
fclose(file);
}

The rest of main can be found here: 主要的其余部分可以在这里找到:

int main() {

size_t size = (int)100 * sizeof(float);
float * val = malloc(size);

// Read the data into an array.
int arraySize = readFile(val, size);

//Test that the array is readable.
for (int i = 0; i < 5; i++) printf("val[%d]=%f\n", i, val[i]);

// Save the array to a text file, with the size of the array as the first element.
writeFile(val,arraySize);

}
        double* val_temp = realloc(val, size);
        if (val_temp == NULL) {
            printf("Realloc failed.\n");
        }
        else {
            val = val_temp;

The caller of this function has no way to know that you've moved the array to a different place. 此函数的调用者无法知道您已将数组移至其他位置。 It's still got the old, now invalid, pointer. 它仍然有旧的,现在无效的指针。

You have a similar problem with size . 您在size也有类似的问题。 How does the caller know you changed it? 呼叫者如何知道您进行了更改?

You choice of division of responsibilities is poor. 您选择的责任划分很差。 If the caller is responsible for allocating the buffer, then this function should ask the caller to enlarge it. 如果调用方负责分配缓冲区,则此函数应要求调用方扩大缓冲区。 If this function is responsible for allocating the buffer, it should allocate it. 如果此函数负责分配缓冲区,则应分配它。 It's generally a very bad idea to split up the responsibility for managing the allocation of a chunk of memory, and this shows one of the reasons why. 分散管理一块内存分配的责任通常是一个非常糟糕的主意,这显示了原因之一。

Perhaps pass in a pointer to a structure that contains a pointer to a buffer and its size? 也许传入一个指向包含缓冲区及其大小的指针的结构的指针? That will work, but still shows poor division of responsibilities. 可以,但是仍然显示责任分工不佳。

Perhaps have this function allocate the buffer and return a structure that includes a pointer to it and the number of elements in it? 也许此函数分配了缓冲区并返回了一个结构,该结构包含一个指向它的指针以及其中的元素数?

If you really want to to do things this way, consider passing the function a pointer to a structure that includes a pointer to the array, the size of the array, and a pointer to a function that resizes the array. 如果您确实想以这种方式执行操作,请考虑将函数的指针传递给结构,该结构包括指向数组的指针,数组的大小以及指向用于调整数组大小的函数的指针。 The caller can, of course, set this pointer to point to the realloc function (though it's probably better for it to be a function that changes the pointer and size members of the structure). 当然,调用者可以将此指针设置为指向realloc函数(尽管最好是将其更改为结构的指针和大小成员的函数)。

You could also use code like this: 您还可以使用如下代码:

struct float_buffer
{
    float* buffer;
    int size;
};

struct float_buffer allocate_float_buffer(int size)
{
    struct float_buffer buf;
    buf.buffer = malloc (size * sizeof(float));
    buf.size = size;
    return buf;
}

bool resize_float_buffer(struct float_buffer* buf, int size)
{
    float* tmp = realloc(buf->buffer, size * sizeof(float));
    if (tmp == NULL)
        return false;
    buf->buffer = tmp;
    buf->size = size;
    return true;
}

And then pass the function a struct float_buffer * . 然后向函数传递一个struct float_buffer *

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM