2016-04-28 94 views
0

我想把一个指针传给一个函数。在这个函数中我使用了malloc来保留空间。问题是当我在main函数中返回时,程序没有响应。这里是我的代码Symplified公司:在函数里面的malloc用法

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
int def(char **B){ 
    int i; 
    B = malloc(3 * sizeof(char)); 
    for(i = 0; i < 2 ; i++){ 
     B[i] = malloc(5 * sizeof(char)); 
    } 
    for(i = 0; i < 2 ; i++){ 
     scanf("%s" , B[i]); 
    } 
    for(i = 0; i < 2 ; i++){ 
     printf("%s\n" , B[i]); 
    } 
    return 0; 
} 

int main(int argc, char *argv[]) { 
    char **B; 
    int i; 
    def(B); 
    for(i = 0; i < 2 ; i++){ 
     printf("%s\n" , B[i]); 
    } 
    return 0; 
} 
+1

请缩进代码; –

+0

当你完成它时,你需要在指针上调用free()。 – Samuel

+0

请勿使用幻数。如果您必须使用'#define'对代码进行硬编码,以便每个用法都引用单个定义。这样一来,为内存分配的元素数量就不会那么容易,而且代码将很容易维护。而且,你是否意识到只能在不受限制的'scanf'语句中输入一个4个字符的字符串。 –

回答

2
int def(char **B) 

应该已经

char** def(char **B) 

和它的返回值应该是

return B; 
/* else the memory allocated inside the function will be freed at 
    * the end and by accessing it later you have undefined behavior for the 
    * rest of the program 
    */ 


B = malloc(3 * sizeof(char)); 

应该已经

B = malloc(3 * sizeof(char*)); // you have two levels of indirection. so char* first 


for(i = 0; i < 2 ; i++) // similary with the other for loops 

应该已经

for(i = 0; i < 3 ; i++) // you used 3 in the above step 


def(B); 

应该已经

B=def(B); 

它是用free()释放所分配的内存,虽然它会在程序结束时自动释放一个很好的做法

+0

这不能解决问题。所有这些都是分配一堆内存,当函数返回时会丢失这些内存。 –

+0

@TomKarzes:没有注意到,在乞讨。但现在修好了 – sjsam

+0

'B = def(B);' - 真的吗?传递'B'毫无意义。此外,由于您需要编写一个很好的答案,请提及malloc可能会失败,即测试返回值。 – 4386427

0

你似乎试图分配一个字符串列表,但是您不提供在def函数之外引用该字符串的能力。你的问题的第一部分是,你必须提供一个指向您的列表:

int def(char ***B) { 

另一种选择是回到您创建的指针:在你分配你的第一个的malloc其次

char** def() { 

空间为3 chars但你需要char指针。 sizeof char != sizeof char*

B = malloc(3 * sizeof(char)); 

应该是:

*B = malloc(3 * sizeof char*); 

而且你应该使用const int#define来定义你的尺寸的常数,所以你不小心在不同的地方得到错误的大小,例如。

#define SIZE_OF_LIST 3 
int def(char ***B){ 
    int i; 
    B = malloc(SIZE_OF_LIST * sizeof(char)); 
    for(i = 0; i < SIZE_OF_LIST ; i++){ 

最后,当你通过函数指针def你需要这样做(上适应第一个变化):

def(&B); 

B = def(); 
+0

这不能解决问题。所有这些都是分配一堆内存,当函数返回时会丢失这些内存。 –

+0

@TomKarzes在您评论,修正之前,我意识到这一点。 –

1

似乎您试图malloc看起来像一个二维数组(或者说是一个字符串数组)的东西。

然而,

def(B); 

是价值的看涨所以B不改变函数返回时。

如果你想改变B需要

def(&B); 

,然后你需要修改相应的函数签名 - 那么你会一个三星级的程序员。

如果你想这样做,正确的,那么阅读:

Create 2D array by passing pointer to function in c

和阅读@Lundin给出了答案 - 这就是做

+0

然后这些类型是错误的。这是一个非常不完整的答案。 –

+0

@TomKarzes - 确切地说,这是代码问题的第2步 – 4386427

+0

引入第三级间接引用而不是'返回'指针从函数到'main'。 – ameyCU

0

其实,这是比这更糟糕的方式。所有C函数参数都是“按值”,这意味着函数内部的变量是在调用时传入的变量的本地副本。所以,当你给一个参数赋值时(你可以这样做,除非它被声明为'const'[我认为C++的'const'现在已经被C采用了]),你不是赋值给变量在通话中传递。因此,在这种情况下,声明

B = malloc(3 * sizeof(char *)); 

不会改变指针的B 的main()宣布;它只是泄漏内存。假设你真的需要这个功能返回INT,则需要添加间接的层次:

int def(char ***B){ 
    *B = malloc(3 * sizeof(char *)); 
    for(i=0; i<2; i++){ 
     (*B)[i] = malloc(5 * sizeof(char)); 
    } 
    ... 
} 

... 

char **B; 
... 
def(&B); /* Note the 'address-of' operator! */ 

如果返回不必是INT:消除参数高清( ),将其更改为返回**** char **,直接返回第一个malloc()的结果,并将呼叫更改为B = def();

0

您的问题是,当你调用def(B),你正在创建一个char **这是一个复制的B。如果更改此新的B,则更改不会反映在主功能上,因为它们是由B的副本制作的。

您应该使用char ***并调用def(&B)(我不认为这是一个好办法,寿),或者你可以有B在主初始化,并呼吁def(B)到alloc和读取其char *,或者你可以返回新B

此外,请检查其他答案中指出的问题。