从函数中将 pointer/array 传递给 main()
Passing pointer/array to main() from a function
我正在学习 functions/pointers,但遇到了一些问题。我需要编写的是一个带有 main()
和另外两个函数的 C 程序。
要求:
read_funct()
必须使用 malloc()
分配足够的内存来存储数据。
read_funct
的函数原型必须是:
int read_funct(int *data_num, double **data_vals, char *filename)
工作原理:
main()
调用第一个函数:read_funct()
read_num()
从文件中读取二进制数据。必须提取两个值:编号。值(前 4 个字节),然后是值本身(每个 8 个字节,因此包含在接下来的 8* 个值中)。这些对应于 data_num
和 data_vals
。它们必须被打印,程序然后 returns 到 main()
.
main()
执行操作以编辑第一个文件中的数据。
main()
调用第二个函数:write_funct()
,将编辑后的数据写入新文件。
我所在的位置:
第一个函数正确读取data_num
,reads/prints data_vals
。这一切都正常工作。然而,我试图在 main()
中打印这些以验证我是否在正确的数据上执行操作,但我无法让它工作。
注意:目前我并没有尝试让它与 write_funct()
一起使用,只是逐步进行。
这是我当前 main()
的代码:
int read_funct(int *data_num, double **data_vals, char *filename);
int main()
{
int data_num;
double **data_vals;
//Reads file using read_funct()
read_funct(&data_num, data_vals, filename);
//Check: print data_num
printf("\nCheck No. of Values: %d\n", data_num);
//Check: print data_vals
for(int i = 0; i<data_num; i++)
{
printf("%0.3lf\t", data_vals[i]);
}
return(0);
}
这是read_funct(
)
int read_funct (int *data_num, double **data_vals, char *filename)
{
FILE * fp = fopen(filename, "rb"); //Opening file
//There's code here to check valid file open
//There's code here to determine size and check valid length
//Proceed with reading data_num if file is large enough
char buffer_n[4];
fread(buffer_n, 4, 1, fp);
int res = buffer_n[0]|(buffer_n[1] << 8)|(buffer_n[2] << 16)|(buffer_n[3] << 24); //Convert endian
data_num = &res; //Passes results back to data_num
printf("Number of Data Values: %d \n", *data_num); //Printing results
//Proceeds with calculating data_vals
data_vals = malloc(8*res); //Allocating memory
fread(data_vals, 8, res, fp);
//Prints data_vals
for(int i=0; i<res; i++)
{
printf("%0.3f\t", data_vals[i]);
}
printf("\nEnd of File Read.\n\n");
fclose(fp);
free(data_vals); //Free allocated memory
return(0);
}
期望输出:
基本上,我希望它从 read_file()
中打印出值,然后在 main()
中打印一个支票,因此输出将类似于:
No. of values: 3 //From printf in read_file()
2 4 6
Check No. of values: 3 //From printf in main()
2 4 6
我认为我哪里出错了:
可以肯定的是,主要问题是我弄乱了我的指针以及我如何初始化 main()
中的内容。我一直试图自己解决这个问题,但我认为我需要一些更有经验的帮助来解决这个问题。
我知道每个 malloc()
调用都必须有一个后续的 free()
,但我担心按照我的方式这样做,也许我已经做到了以便我无法在 main()
中检索它。它是否需要有一个中间缓冲区来代替分配内存?
如果能帮助使此代码正常工作,我们将不胜感激。谢谢!
是的,您过早释放了缓冲区。释放它之后,无法保证它包含什么。你可以在最后释放它,在 main.
除了过早释放数据外,您还有另一个问题:
double **data_vals;
read_funct(&data_num, data_vals, filename);
如果你想让data_vals
被一个函数填充(写入,修改),你必须传递它的地址,就像你对data_num
所做的那样。
这是另一个略有不同的解释。你看,你声明了 data_vals
但你没有给它赋值——它包含垃圾。所以将 data_vals
传递给任何函数,或在任何表达式中使用它都是无意义的。它 有一种意义 相反,可以通过直接分配或传递 它的地址 来 分配 一些东西给它给一个函数,为函数填充变量。
那么,你对data_vals
的用法描述了一个向量,或者数组。所以你真的需要用[]
声明一个数组,或者可能是一个指针(指针和数组在C中相当related/interchangeable)。 main() 函数的逻辑需要一个指针,而不是 指向指针 的指针。因此,这是合适的:
double *data_vals;
写入指针变量的函数需要要写入的变量地址;换句话说:一个 指向一个指针 的指针。这就是为什么你的函数有这个(正确的)签名:
read_funct(..., double **data_vals, ...)
为了方便理解,让我们看看你写对的另一个(更简单的)东西:
int data_num;
read_funct(&data_num, ...); // declaration: read_funct(int *data_num, ...)
您在 main() 中将 data_num
声明为整数;你用指向整数的指针的形式参数声明read_funct(),然后你调用read_funct()传递地址 你的变量 data_num
。完美的。现在,对另一个变量 data_vals
执行相同的操作。您将其声明为 指向 double 的指针,使用符号 &data_vals
将其地址传递给 read_funct(),并且您的函数 read_funct() 声明参数作为指向 double 的指针的 指针(并使用 *data_vals = ...
写入它。您可以看到两个变量之间的并行性,对吧?
可能是我太迂腐了,但你的问题真的很清楚,格式也很好,所以我也尝试这样做。
我正在学习 functions/pointers,但遇到了一些问题。我需要编写的是一个带有 main()
和另外两个函数的 C 程序。
要求:
read_funct()
必须使用malloc()
分配足够的内存来存储数据。read_funct
的函数原型必须是:int read_funct(int *data_num, double **data_vals, char *filename)
工作原理:
main()
调用第一个函数:read_funct()
read_num()
从文件中读取二进制数据。必须提取两个值:编号。值(前 4 个字节),然后是值本身(每个 8 个字节,因此包含在接下来的 8* 个值中)。这些对应于data_num
和data_vals
。它们必须被打印,程序然后 returns 到main()
.main()
执行操作以编辑第一个文件中的数据。main()
调用第二个函数:write_funct()
,将编辑后的数据写入新文件。
我所在的位置:
第一个函数正确读取data_num
,reads/prints data_vals
。这一切都正常工作。然而,我试图在 main()
中打印这些以验证我是否在正确的数据上执行操作,但我无法让它工作。
注意:目前我并没有尝试让它与 write_funct()
一起使用,只是逐步进行。
这是我当前 main()
的代码:
int read_funct(int *data_num, double **data_vals, char *filename);
int main()
{
int data_num;
double **data_vals;
//Reads file using read_funct()
read_funct(&data_num, data_vals, filename);
//Check: print data_num
printf("\nCheck No. of Values: %d\n", data_num);
//Check: print data_vals
for(int i = 0; i<data_num; i++)
{
printf("%0.3lf\t", data_vals[i]);
}
return(0);
}
这是read_funct(
)
int read_funct (int *data_num, double **data_vals, char *filename)
{
FILE * fp = fopen(filename, "rb"); //Opening file
//There's code here to check valid file open
//There's code here to determine size and check valid length
//Proceed with reading data_num if file is large enough
char buffer_n[4];
fread(buffer_n, 4, 1, fp);
int res = buffer_n[0]|(buffer_n[1] << 8)|(buffer_n[2] << 16)|(buffer_n[3] << 24); //Convert endian
data_num = &res; //Passes results back to data_num
printf("Number of Data Values: %d \n", *data_num); //Printing results
//Proceeds with calculating data_vals
data_vals = malloc(8*res); //Allocating memory
fread(data_vals, 8, res, fp);
//Prints data_vals
for(int i=0; i<res; i++)
{
printf("%0.3f\t", data_vals[i]);
}
printf("\nEnd of File Read.\n\n");
fclose(fp);
free(data_vals); //Free allocated memory
return(0);
}
期望输出:
基本上,我希望它从 read_file()
中打印出值,然后在 main()
中打印一个支票,因此输出将类似于:
No. of values: 3 //From printf in read_file()
2 4 6
Check No. of values: 3 //From printf in main()
2 4 6
我认为我哪里出错了:
可以肯定的是,主要问题是我弄乱了我的指针以及我如何初始化
main()
中的内容。我一直试图自己解决这个问题,但我认为我需要一些更有经验的帮助来解决这个问题。我知道每个
malloc()
调用都必须有一个后续的free()
,但我担心按照我的方式这样做,也许我已经做到了以便我无法在main()
中检索它。它是否需要有一个中间缓冲区来代替分配内存?
如果能帮助使此代码正常工作,我们将不胜感激。谢谢!
是的,您过早释放了缓冲区。释放它之后,无法保证它包含什么。你可以在最后释放它,在 main.
除了过早释放数据外,您还有另一个问题:
double **data_vals;
read_funct(&data_num, data_vals, filename);
如果你想让data_vals
被一个函数填充(写入,修改),你必须传递它的地址,就像你对data_num
所做的那样。
这是另一个略有不同的解释。你看,你声明了 data_vals
但你没有给它赋值——它包含垃圾。所以将 data_vals
传递给任何函数,或在任何表达式中使用它都是无意义的。它 有一种意义 相反,可以通过直接分配或传递 它的地址 来 分配 一些东西给它给一个函数,为函数填充变量。
那么,你对data_vals
的用法描述了一个向量,或者数组。所以你真的需要用[]
声明一个数组,或者可能是一个指针(指针和数组在C中相当related/interchangeable)。 main() 函数的逻辑需要一个指针,而不是 指向指针 的指针。因此,这是合适的:
double *data_vals;
写入指针变量的函数需要要写入的变量地址;换句话说:一个 指向一个指针 的指针。这就是为什么你的函数有这个(正确的)签名:
read_funct(..., double **data_vals, ...)
为了方便理解,让我们看看你写对的另一个(更简单的)东西:
int data_num;
read_funct(&data_num, ...); // declaration: read_funct(int *data_num, ...)
您在 main() 中将 data_num
声明为整数;你用指向整数的指针的形式参数声明read_funct(),然后你调用read_funct()传递地址 你的变量 data_num
。完美的。现在,对另一个变量 data_vals
执行相同的操作。您将其声明为 指向 double 的指针,使用符号 &data_vals
将其地址传递给 read_funct(),并且您的函数 read_funct() 声明参数作为指向 double 的指针的 指针(并使用 *data_vals = ...
写入它。您可以看到两个变量之间的并行性,对吧?
可能是我太迂腐了,但你的问题真的很清楚,格式也很好,所以我也尝试这样做。