2010-10-01 47 views
0

當我調試下面的代碼時,strncpy工作正常,但只要循環退出,我看到parent_var_names指向NULL/0xfdfdfddf。我很困惑!奇怪的char **/calloc行爲

parent_var_names = (const char**)calloc(net->nodes[x]->num_parents, sizeof(const char*)); 
for(int i(1); i < net->nodes[x]->num_parents; ++i) 
{ 
    parent_var_names[i] = (const char*)malloc(strlen(rhs_arr[net->nodes[x]->markov_parents[i]])); 
    strncpy((char*)parent_var_names[i], (char*)rhs_arr[net->nodes[x]->markov_parents[i]], strlen(rhs_arr[net->nodes[x]->markov_parents[i]])); 
} 
+6

C或C++?選一個。最好不要成爲C++。 – GManNickG 2010-10-01 20:53:38

+0

好吧。它是一個C++編譯器。 – jmgunn87 2010-10-01 20:54:20

+1

你確定你所有的rhs_arr [net-> nodes [x] - > markov_parents [i]]字符串都是空終止的嗎?你的parent_var_names字符串將不會。 – MerickOWA 2010-10-01 20:54:24

回答

3

int i(1)for環路初始化大概應該是int i(0)

否則,您從不將parent_var_names[0]設置爲以外calloc()將其初始化爲的任何內容。

只是爲了完整性(因爲在評論中提及了幾次),所以您沒有考慮到要複製的字符串的'\ 0'終止符。由於您沒有複製strncpy()調用中的終止符,因此您不會溢出分配的緩衝區,但結果不是正確終止的字符串。這可能是你的意圖,但這是不尋常的。如果有意的話,請在那裏發表評論...

1

如果您的parent_var_names不是NULL終止,那可能是因爲您在爲字符串分配空間時正在使用strlen。這無法爲字符串創建NULL終止符的空間。改爲嘗試strlen()+1

你或許應該使用的std :: string反正...

+0

好吧,我休息一下,再次用新鮮的眼睛看看。 int i(1)是明顯的錯誤。我複製並粘貼進入該循環的文件(現在我知道爲什麼這是一個不 - 不!)。有時當你在屏幕上盯着屏幕幾個小時時,你看不到明顯的盯着你的臉。無論如何都歡呼。 – jmgunn87 2010-10-02 00:38:04

+0

我如何評價這裏的人? – jmgunn87 2010-10-02 00:38:26

+0

哦和blastfurnace ..關於下午你發給我..我承認錯誤是從來沒有由你?我認爲你可能沒有努力工作,發生了這種事。學習一些謙卑。如果我不知道大多數編程語言中的數組都是0索引的,我不認爲我會做得很多,並相信我我做的。 – jmgunn87 2010-10-02 00:48:37

3

配售保護字節(即0xFDFDFDFD)圍繞分配的內存區域是(微軟)調試堆的一個特徵。看到你遇到這個值,或者意味着你在某處覆蓋了內存,或者你正在查看parent_var_names[0]的值,而沒有真正寫入任何內容(即仔細看看初始化循環變量i的值)。

此外,你的代碼可以簡化爲:

#include <string> 
/* ... */ 

int ii = 0; 
int parent_count = net->nodes[x]->num_parents; 
char** parent_var_names = calloc(parent_count, sizeof(char*)); 

for(; ii < parent_count; ++ii) 
{ 
    parent_var_names[ii] = strdup(rhs_arr[net->nodes[x]->markov_parents[ii]]); 
} 

另外,還要確保你的markov_parents是絕對零結尾。順便說一句,在迴應你的意見,你想「C和C++兼容性」:你的代碼是無效的C代碼,所以...