1

main 関数でprintfmyarray[x]を実行すると、データが表示されない (空白行が表示される) のはなぜですか? 配列は正しく入力されています (関数で出力すると値が得られます)

これが私のコードです:

int main(void)  {
    char thisxpath[300];
    char thisurl[200];
    char** myarray = NULL;
    strcpy (thisurl,"http://api.openweathermap.org/data/2.5/weather?q=Pescara&mode=xml&units=metric");
    strcpy (thisxpath,"//city/@name | //country | //weather/@value | //temperature/@value | //precipitation/@value | //humidity/@value | //speed/@*[name()='name' or name()='value']");
    xmlretrive (thisurl, thisxpath, &myarray);

    printf("%s\n", myarray[1]);

    free(myarray);
    return 0;
}

void xmlretrive(char* myurl, char* myxpath, char** myarray) {

    //code that retrieve with cURL the XML and other stuff
    //keyword contain data, that are copied into myarray

    myarray = malloc(20 * sizeof(char*));   
    for (i=0; i < nodeset->nodeNr; i++) {
    keyword = xmlNodeListGetString(doc, nodeset->nodeTab[i]->xmlChildrenNode, 1);
    myarray[i] = malloc((100) * sizeof(char));
    strcpy(myarray[i], keyword);
    // if I printf("%s\n", myarray[i]) here I can see that array is actually filled
    xmlFree(keyword);
}
4

1 に答える 1

5

myarrayのコピーをに渡していますxmlretrivemyarray内部のポイントを変更したい場合はxmlretrive、ポインタを渡す必要があります。つまりchar***

void xmlretrive(char* myurl, char* myxpath, char*** myarray) {
    *myarray = malloc(20 * sizeof(char*));   
    for (i=0; i < nodeset->nodeNr; i++) {
        keyword = xmlNodeListGetString(doc, nodeset->nodeTab[i]->xmlChildrenNode, 1);
        (*myarray)[i] = malloc(strlen(keyword)+1);
        if ((*myarray)[i] == NULL) {
            // out of memory.  print error msg then exit
        }
        strcpy((*myarray)[i], keyword);
        xmlFree(keyword);
}

また、あなたのmalloc行にいくつかの変更を提案したことに注意してください

  • malloc からのリターンをキャストしないでください
  • keywordのバッファオーバーフローの可能性を回避するために必要な文字列の正確な長さを割り当てますstrlen(keyword)>99
  • sizeof(char)1であることが保証されているため、割り当てサイズにそれを掛ける必要はありません

これで差し迫った問題は解決しますが、適切に機能させるには不十分な場合があります。その他の考慮事項:

  • mainfree割り当てられた各メンバーとmyarrayそれmyarray自体を呼び出す必要があります
  • mainの長さを知る方法はありませんmyarraylength別の引数を渡すか、配列の最後に要素を追加するようにxmlretrive変更して、これが見つかるまで繰り返すことができますxmlretriveNULLmain
  • xmlretrive20の長さをハードコーディングするのではなく、おそらくnodeset->nodeNr + 1(+1は配列にターミネータを追加すると仮定します)要素にスペースを割り当てる必要がありますNULL
于 2013-06-17T10:34:30.620 に答える