我正在玩C中的双指针,并且想知道我是否创建了一个初始化表的函数,当我尝试使用InitStringTable分配的内存时,它会在返回main时崩溃。我相信一个简单的解决方法是使strTable全局化,然后我相信它没问题,但我不想这样做,因为这对我来说是一个学习练习,可以通过表格进行修改,即我应该能够修改strTable来自在InitStringTable之后的main或另一个函数modifyTable。 感谢您提供任何帮助。
int main()
{
char** strTable;
// Allocates memory for string table.
InitStringTable(strTable);
// Below lines should be able to copy strings into newly allocated table.
// Below lines cause crash however.
strcpy(strTable[0], "abcdef");
strcpy(strTable[1], "xy");
}
// Allocates memory for the string table. This function should create a table
// of size 10 strings with each string 50 chars long. The code compiles fine.
void InitStringTable(char** table)
{
int i = 0;
table = (char**)malloc(sizeof(char)*10);
for(i = 0; i < 10; i++)
{
table[i] = (char*)malloc(sizeof(char)*50);
}
for(i = 0; i < 10; i++)
{
memset(table[i], 0, 50);
}
strcpy(table[0], "string1");
}
答案 0 :(得分:5)
C是按值传递的。
从table
返回时,分配给InitStringTable()
的值会丢失。
同样,在分配指向char
的指针时,请求指向char
的指针。
所以这个:
... = (char**)malloc(sizeof(char)*10);
至少应为(假设C):
... = malloc(sizeof(char*)*10);
可能的方法是:
#include <stdlib.h>
#include <string.h>
#include <errno.h>
int InitStringTable(char *** ppptable, const size_t n, const size_t l)
{
int result = 0;
if (NULL == ppptable)
{
result = -1;
errno = EINVAL;
}
else
{
(*ppptable) = malloc(n * sizeof(**ppptable));
if (NULL == (*ppptable))
{
result = -1;
}
else
{
size_t i = 0;
for(; i < n; ++i)
{
(*ppptable)[i] = calloc(l, sizeof(*(*ppptable)[i]));
if (NULL == (*ppptable)[i])
{
result = -1;
/* Failing in the middle requires clean-up. */
for (; i > 0; --i)
{
free((*ppptable)[i-1]);
}
free(*ppptable);
(*ppptable) = NULL;
break;
}
}
}
}
return result;
}
这样称呼:
#include <stdlib.h>
#include <stdio.h>
int InitStringTable(char *** ppptable, const size_t n, const size_t l);
int main(void)
{
int result = EXIT_SUCCESS;
char ** strTable = NULL;
if ( -1 == InitStringTable(&strTable, 10, 42)) //* Allocate array with 10 "strings" à 42 chars. */
{
perror("InitStringTable() failed");
result = EXIT_FAILURE;
}
else
{
strcpy(strTable[0], "abcdef");
strcpy(strTable[1], "xy");
}
return result;
}
不,我不会陷入这种荒谬的过程中#34;你不想成为一名三星级程序员!&#34;讨论
答案 1 :(得分:0)
你有指针问题。
如果你说:
void inc(int a){
a++;
}
int main(){
int a = 0;
inc(a);
printf ("%d\n", a); // will display 0, not 1
}
不起作用。
您必须将&strTable
代替strTable
作为InitStringTable
参数,然后更改InitStringTable
中的其他内容。
或者只做strTable = InitStringTable()
; ,并从char**
返回InitStringTable
。
答案 2 :(得分:0)
InitStringTable()下面的行崩溃,因为他们正在尝试执行操作 在一个与他们的范围不同的内存地址上,也没有任何引用 记忆地址。
函数InitStringTable()为表分配内存,但无法访问
调用函数(这里是main),因为内存是函数所在的本地
分配。
因此,为了使用相同的内存地址进行操作
调用函数必须将该地址的引用传递给调用函数。
在你的程序中,你可以这样做:
将函数声明为: -
char **InitStringTable(char **);
int main()
{
char** strTable;
strTable = InitStringTable(strTable);
strcpy(strTable[0], "abcdef");
strcpy(strTable[1], "xy");
}
char **InitStringTable(char** table)
{
int i = 0;
table = (char**)malloc(sizeof(char)*10);
for(i = 0; i < 10; i++)
{
table[i] = (char*)malloc(sizeof(char)*50);
}
for(i = 0; i < 10; i++)
{
memset(table[i], 0, 50);
}
strcpy(table[0], "string1");
/* after the function has finished its job, return the address of the table */
return table;
}