所以我试图让用户输入一个数字,然后将该值存储在动态数组中。首先是代码:
#include <stdio.h>
#include <stdlib.h>
//dynamically grow the array
void growArray(int *arr, int *size){
//double the size of the array
printf("Resizing array\n");
int *temp = malloc( *size * 2 * sizeof(int));
printf("Malloc was succesfuly\n");
int i;
for (i = 0; i < *size; i++)
temp[i] = arr[i];
printf("About to free arr\n");
printf("arr: %p", arr);
printf("temp: %p", temp);
free(arr);
arr = malloc( *size * 2 * sizeof(int));
printf("About to change value to arr\n");
arr = temp;
free(temp);
printf("About to change the value of size\n");
*size *= 2;
printf("New size: %d\n", *size);
}
int main(){
int *dynamicArr;
int *size;
*size = 1;
dynamicArr = (int*) malloc(sizeof(int));
int value, i;
i = 0;
do{
printf("\nPlease enter in a int value: ");
scanf("%d", &value);
//check if the array needs to be resizesd;
printf("Checking if size if sufficient\n");
if (i >= *size)
growArray(dynamicArr, size);
if (value != -999){
printf("Adding value to the array\n");
dynamicArr[i] = value;
i ++;
}
}while(value != -999);
for (i = 0; i < *size; i++){
printf("Value of dynamicArr[%d]: %d\n", i, dynamicArr[i]);
}
return 0;
}
正如你所看到的,我有一堆打印语句,我可以看到我的程序在什么时候,以及它当前在做什么。所以,该计划最初是有效的。我能够成功添加8个值(并将数组调整大小3次,从大小1到大小8)。但是当我添加我的9值时,它必须调整数组的大小,其中调用方法growArray()。但是,由于某种原因,我收到以下错误:
*** Error in `./a.out': free(): invalid next size (fast): 0x0000000000e69010 ***
Segmentation fault (core dumped)
在出错之前,printf(“关于自由arr”)有效,但是printf(“arr:%p”,arr);不叫。
我不知道为什么会这样,一些帮助会非常感激。
答案 0 :(得分:2)
您的代码应该看起来更像这样:
#include <stdio.h>
#include <stdlib.h>
int main() {
int size = 1;
int *dynamicArr = malloc(size * sizeof(*dynamicArr));
int idx = 0;
while (1) {
int value;
printf("\nPlease enter in a int value: ");
scanf("%d", &value);
if (value == -999) {
break;
}
//check if the array needs to be resizesd
printf("Checking if size if sufficient\n");
if (idx >= size) {
size *= 2;
dynamicArr = realloc(dynamicArr, size * sizeof(*dynamicArr));
}
printf("Adding value to the array\n");
dynamicArr[idx++] = value;
}
int i;
for (i = 0; i < idx; i++) {
printf("Value of dynamicArr[%d]: %d\n", i, dynamicArr[i]);
}
free(dynamicArr);
return 0;
}
或者如果您想坚持实施:
#include <stdio.h>
#include <stdlib.h>
//dynamically grow the array
void growArray(int **arr, int *size){
//double the size of the array
printf("Resizing array\n");
int *temp = malloc( *size * 2 * sizeof(int));
printf("Malloc was succesfuly\n");
int i;
for (i = 0; i < *size; i++)
temp[i] = (*arr)[i];
printf("About to free arr\n");
printf("arr: %p\n", *arr);
printf("temp: %p\n", temp);
free(*arr);
printf("About to change value to arr\n");
*arr = temp;
printf("About to change the value of size\n");
*size *= 2;
printf("New size: %d\n", *size);
}
int main() {
int size = 1;
int *dynamicArr = malloc(size * sizeof(*dynamicArr));
int idx = 0;
while (1) {
int value;
printf("\nPlease enter in a int value: ");
scanf("%d", &value);
if (value == -999) {
break;
}
//check if the array needs to be resizesd;
printf("Checking if size if sufficient\n");
if (idx >= size) {
growArray(&dynamicArr, &size);
}
printf("Adding value to the array\n");
dynamicArr[idx++] = value;
}
int i;
for (i = 0; i < idx; i++){
printf("Value of dynamicArr[%d]: %d\n", i, dynamicArr[i]);
}
free(dynamicArr);
return 0;
}
顺便说一句,您可以使用memcpy将整个现有数组复制到临时数组。
答案 1 :(得分:1)
原始代码中存在一些问题。
(a)参数arr
按值传递给growArray
,因此您的作业arr = malloc(...)
和arr = temp
不会更新main()
中引用的变量只有growArray
本地的副本。另一方面,当您调用free(arr)
时,您正在释放dynamicArr
中变量main()
指向的缓冲区。这是您的段错误的直接原因。
(b)当您分配arr = temp
然后free(temp);
时,您泄漏了malloc()
刚刚上方的缓冲区,然后释放您指定的缓冲区arr
指向(离开)它摇摇晃晃)。
void growArray(int *arr, int *size){
输入growArray
时,arr
指向缓冲区,A
...
int *temp = malloc( *size * 2 * sizeof(int));
temp
被初始化为指向新缓冲区B
...
free(arr);
原始缓冲区A被释放。局部变量arr
现在是一个悬空指针,就像调用者按照值传递到此例程中的指针一样。
arr = malloc( *size * 2 * sizeof(int));
arr
设置为新分配的缓冲区C。
...
arr = temp;
arr
设置为别名temp
,指向缓冲区B.缓冲区C泄露。
free(temp);
释放temp
和arr
指向的缓冲区B.他们现在都是悬挂指针。 arr
稍后
...
}
tmp
和arr
都超出了范围。缓冲区B和C泄漏。
int main(){
int *dynamicArr;
int *size;
*size = 1;
dynamicArr = (int*) malloc(sizeof(int));
dynamicArr指向malloced缓冲区 ... 做{ ... 如果(...){ growArray(dynamicArr,size); ... }
第一次if条件通过时,dynamicArr
的值作为参数arr
传递给growArray。 growArray
释放它指向的缓冲区,然后分配和泄漏一些内存而不影响dynamicArr
的本地值。 dynamicArr
现在是一个悬垂的指针。
if (value != -999){
...
dynamicArr[i] = value;
然后这会访问悬空指针和段错误。