C 中的内存管理命令行参数
Memory Management Command Line Arguments in C
我正在编写一个简单的程序,它接受命令行参数并将它们存储到一个 char ** 中。我正在尝试了解有关内存管理的更多信息,但无法克服这个简单的绊脚石。我的程序应该将命令行参数复制到动态分配的 char ** 中。然而,我数组中的第一个位置总是更糟。下面是代码及其打印的内容:
if (strcmp(argv[1], "test") ==0)
{
test();
}
else
{
char ** file_names = malloc(10);
for(int i =0; i < argc-1; ++i)
{
file_names[i] = malloc(10);
strcpy(file_names[i], argv[i+1]);
printf("%s, %s\n", argv[i+1], file_names[i]);
}
printf("____________\n");
for(int i =0; i < argc-1; ++i)
{
printf("%s\n", file_names[i]);
}
}
结果是:
what, what
test, test
again, again
wow, wow
____________
pK@??
test
again
wow
有人可以解释为什么会这样吗?谢谢
这个:
char ** file_names = malloc(10);
是一个错误。它尝试分配 10 个字节,这与您需要多少字节无关。分配不足然后覆盖会给您未定义的行为。
应该是这样的:
char **file_names = malloc(argc * sizeof *file_names);
这通过乘以参数的数量来计算分配的大小(argc
,如果你不想存储 argv[0]
那么这应该是 (argc - 1)
,当然) 为字符指针的大小,表示为sizeof *file_names
。由于file_names
是char * *
类型,*file_names
的类型是char *
,这就是你想要的。这是一个通用模式,可以经常应用,并且可以让您停止重复类型名称。它可以保护您免受错误。
例如比较:
double *floats = malloc(1024 * sizeof(float)); /* BAD CODE */
和:
double *floats = malloc(1024 * sizeof *floats);
如果您想象它最初是 float *floats
(顾名思义),那么第一个变体包含另一个分配不足的错误,而第二个 "survived" 类型更改没有错误。
然后你需要检查它是否成功,然后再假设它成功了。
您想为 file_names
分配合适的内存量,可能更像是:
char ** file_names = malloc(sizeof(char*) * (argc - 1));
我正在编写一个简单的程序,它接受命令行参数并将它们存储到一个 char ** 中。我正在尝试了解有关内存管理的更多信息,但无法克服这个简单的绊脚石。我的程序应该将命令行参数复制到动态分配的 char ** 中。然而,我数组中的第一个位置总是更糟。下面是代码及其打印的内容:
if (strcmp(argv[1], "test") ==0)
{
test();
}
else
{
char ** file_names = malloc(10);
for(int i =0; i < argc-1; ++i)
{
file_names[i] = malloc(10);
strcpy(file_names[i], argv[i+1]);
printf("%s, %s\n", argv[i+1], file_names[i]);
}
printf("____________\n");
for(int i =0; i < argc-1; ++i)
{
printf("%s\n", file_names[i]);
}
}
结果是:
what, what
test, test
again, again
wow, wow
____________
pK@??
test
again
wow
有人可以解释为什么会这样吗?谢谢
这个:
char ** file_names = malloc(10);
是一个错误。它尝试分配 10 个字节,这与您需要多少字节无关。分配不足然后覆盖会给您未定义的行为。
应该是这样的:
char **file_names = malloc(argc * sizeof *file_names);
这通过乘以参数的数量来计算分配的大小(argc
,如果你不想存储 argv[0]
那么这应该是 (argc - 1)
,当然) 为字符指针的大小,表示为sizeof *file_names
。由于file_names
是char * *
类型,*file_names
的类型是char *
,这就是你想要的。这是一个通用模式,可以经常应用,并且可以让您停止重复类型名称。它可以保护您免受错误。
例如比较:
double *floats = malloc(1024 * sizeof(float)); /* BAD CODE */
和:
double *floats = malloc(1024 * sizeof *floats);
如果您想象它最初是 float *floats
(顾名思义),那么第一个变体包含另一个分配不足的错误,而第二个 "survived" 类型更改没有错误。
然后你需要检查它是否成功,然后再假设它成功了。
您想为 file_names
分配合适的内存量,可能更像是:
char ** file_names = malloc(sizeof(char*) * (argc - 1));