2011-12-21 59 views
0

我的代码给我段错误的错误:我不明白,调试器说,错误来自从stored_打印值的realloc和strcpy

char *stored_ = NULL; 
char testMessage[15]; 

//strcpy(stored_, testMessage); 

for (int a = 0;a < 10; a++) 
{ 
    sprintf(testMessage,"Message::%i\n",a); 
    printf("string is:%s;length is %i\n",testMessage,strlen(testMessage)); 

    stored_ = (char*) realloc (stored_, sizeof(char) * (strlen(testMessage) * (a+1))); 

    strcpy(&stored_[a], testMessage); 
} 

for (int b = 0;b < 10; b++) 
{ 
    printf("inside:|%s|\n",stored_[b]); 
} 
+0

段错误发生在哪一行? – 2011-12-21 05:23:17

+0

您需要为末尾的空终止字符('\ 0')添加额外空间。 – 2011-12-21 05:32:20

回答

5

拳心向上,sizeof(char)总是 1,你不不需要乘以它。

其次,当你为一个字符串分配房间,你必须使用:

malloc (strlen (string) + 1); 

换句话说,你需要空间在末尾的空字节。

第三,你似乎混淆了字符指针和字符指针指针。 stored_是单个字符块,而stored_[1]只比stored_[0]只有一个字节,这意味着您将没有足够的空间存储字符串。

stored_[n], n=: 0 1 2 3 
       +---+---+---+---+ 
       | | | | |... 
       +---+---+---+---+ 
       each of these cells is a single byte. 

你要么必须管理字符自己的单块,留下足够的空间,每一个元素(通过使用稀疏索引),或具有字符指针与索引0,1,2,依此块打开,但你必须分别管理字符串分配。

下面的代码显示如何做到这一点后者:

#include <stdio.h> 
#include <string.h> 
#include <stdlib.h> 

int main (void) { 
    // An array of char pointers (C strings). 

    char **stored_ = NULL; 
    char testMessage[15]; 
    int i; 

    // Populate them. 

    for (i = 0; i < 10; i++) { 
     sprintf (testMessage,"Message::%i",i); 
     printf ("string is:%s;length is %i\n",testMessage,strlen(testMessage)); 

     // Reallocate array of char *, allocate room for string, then store it. 

     stored_ = realloc (stored_,sizeof (char*) * (i + 1)); 
     stored_[i] = malloc (strlen (testMessage) + 1); 
     strcpy (stored_[i], testMessage); 
    } 

这是它的肉,字符指针分开从形成C字符串的字符的实际阵列的阵列的分配。

然后下面的代码打印它们并清理。

// Print them. 

    for (i = 0; i < 10; i++) { 
     printf("inside:|%s|\n",stored_[i]); 
    } 

    // Free all memory and return. 

    for (i = 0; i < 10; i++) { 
     free (stored_[i]); 
    } 
    free (stored_); 

    return 0; 
} 

输出是如预期:

string is:Message::0;length is 10 
string is:Message::1;length is 10 
string is:Message::2;length is 10 
string is:Message::3;length is 10 
string is:Message::4;length is 10 
string is:Message::5;length is 10 
string is:Message::6;length is 10 
string is:Message::7;length is 10 
string is:Message::8;length is 10 
string is:Message::9;length is 10 
inside:|Message::0| 
inside:|Message::1| 
inside:|Message::2| 
inside:|Message::3| 
inside:|Message::4| 
inside:|Message::5| 
inside:|Message::6| 
inside:|Message::7| 
inside:|Message::8| 
inside:|Message::9| 

在该方法中,每个小区是一个指向字符数组,单独分配(其保持C字符串):

stored_[n], n=: 0 1 2 3 
       +---+---+---+---+ 
       | | | | |... 
       +---+---+---+---+ 
        | | | |  +----------------------+ 
        | | | +---> | character array here | 
        | | |   +----------------------+ 
        | | |   +----------------------+ 
        | | +-------> | character array here | 
        | |    +----------------------+ 
        | |    +----------------------+ 
        | +-----------> | character array here | 
        |     +----------------------+ 
        |     +----------------------+ 
        +---------------> | character array here | 
            +----------------------+ 
+0

第四,它是%d,而不是%i :) – 2011-12-21 05:32:03

+0

实际上,'d'和'i'至少在C99下同样有效。 – paxdiablo 2011-12-21 05:44:12

0

您似乎没有正确计算出stored_的字符串长度。

您将testMessage指定为&stored_[loopindex]的每个循环。我不确定这是否是有意的行为,但这是你正在做的事情,所以我希望你的第10次迭代给出字符串"MMMMMMMMMessage::9\n"

反正testMessage始终是相同的字符数,因此通过stored_所需的存储空间可以被计算为:

strlen(testMessage) // length of str to place at &stored_[a] 
+ a     // the loop index, where you're inserting testMessage 
+ 1     // important! extra char to hold the null terminator 

永远不要忘记+1,在C每个字符串必须有空间为null terminator