【问题标题】:C - Nary Tree: error while appending a new child to the treeC - Nary Tree:将新子级附加到树时出错
【发布时间】:2015-07-27 05:53:33
【问题描述】:

我正在使用这样的结构在 C 中开发 Nary Tree:

typedef struct sNaryNode { 
     int *data; // Point to the node ’s data
     int n; // The number of children 
     struct sNaryNode **child; // The child list
} NaryNode; 

typedef NaryNode NaryTree;

我不能使用列表(项目需要)。 我能够创建树,但是当我尝试将新的孩子附加到树时,树的所有“数据”值都会被新值覆盖。例如:我用data = 1 创建根,然后我想用data = 2 追加一个新子,最后根和新子都具有相同的“数据”值,即data = 2。我认为问题不是由于指针管理的错误,但由于我不知道我错在哪里,所以我决定征求您的意见。以下是完整代码:
lm_array2.h

#ifndef lm_array2_h
#define lm_array2_h

typedef struct sNaryNode { 
     int *data; // Point to the node ’s data
     int n; // The number of children 
     struct sNaryNode **child; // The child list
} NaryNode; 

typedef NaryNode NaryTree;
typedef void (*DataFreeFunc) (const void *);

void printArrayTree (NaryTree*);
NaryTree *createNode (int, int*);
void freeTree (NaryTree*, DataFreeFunc);
int appendChild(NaryNode*, int*);
void deleteChild (NaryTree*, int, DataFreeFunc);

#endif

lm_array2.c

#include <stdio.h>
#include <stdlib.h>
#include "lm_array2.h"

void printArrayTree (NaryTree *tree) {
    int d = *tree->data;
    printf("\n %d ", d);
    if (tree->n > 0) {
        int i;
        for (i = 0; i < tree->n; i++) {
            //printArrayTree (tree->child[i]);
            int dd = *tree->child[i]->data;
            printf("\n %d", dd);
        }

    }
    else {
        printf("\n-----\n");
        return;
    }
}

NaryTree *createNode ( int children , int *data) { 
    // Allocate space for a new NaryNode in memory
    NaryNode *node = (NaryNode*) calloc (1 , sizeof (NaryNode) );

    // Set the contents of the NaryNode appropriately
    node->data = data; 
    node->n = children ; 
    node->child = (NaryNode**) calloc ( children , sizeof (NaryNode*) );

    // Return the node we initialized
    return node;
}

void freeTree (NaryTree *tree , DataFreeFunc dFree) {
    unsigned i; 

    // Don’ t try this with a NULL pointer 
    if ( tree == NULL) return; 

    // Free the children recursively 
    for ( i = 0; i < tree->n; ++i ) 
        freeTree ( tree->child [ i ] , dFree); 

    // Free the child array 
    free ( tree->child ); 

    // Free the data if a function is provided 
    if (dFree) dFree( tree->data); 

    // And finally , free the structure 
    free ( tree ); 
}

 int appendChild(NaryNode *root , int *data) {
     // Increment the degree of the node 
     root->n++; 

     // Reallocate the child array (n children in the child array) 
     root->child = (NaryNode**) realloc ( root->child , ( root->n)*sizeof (NaryNode*) );

     // Add the newNode into the child array and increment degree 
     root->child [ root->n - 1] = createNode (0 , data); 

     // Return the index of the child we just inserted 
     return root->n - 1;  
 } 

 void deleteChild (NaryTree *root , int idx , DataFreeFunc dFree) {
     unsigned i; 

     // Delete the child 
     freeTree ( root->child [ idx ] , dFree); 

     // Remove the defunct child 
     for ( i = idx ; i < root->n - 1; ++i ) 
        root->child [ i ] = root->child [ i - 1]; 

     // And finally , reallocate 
     root->n--; 
     root->child = (NaryNode**) realloc ( root->child , ( root->n)*sizeof (NaryNode*) );
 }

ma​​in.c

#include <stdio.h>
#include <stdlib.h>
#include "lm_array2.h"
#include "lm_array2.c"

void menu(int*);

int main() {
    NaryTree *aTree = (NaryNode*)malloc(sizeof(NaryNode));
    int choice = 0, value;

    printf("\nEnter the root value: ");
    scanf("%d", &value);
    aTree = createNode (0, &value);

    do {
        menu(&choice);
        switch (choice) {

            case 1:
                printf("\nEnter the new child value: ");
                scanf("%d", &value);
                //NaryTree *aNode = createNode (0, value);
                appendChild(aTree, &value);
                break;

            case 2:
                //printf("%d", *aTree->data);
                printArrayTree(aTree);
                break;

            case 3:
                printf("\n\n***THE END***\n\n");
                break;
        }
    } while (choice > 0 && choice <= 2);

    system("PAUSE");

    return 0;
}

void menu(int *choice){
    printf("\n");
    printf("1. Insert new child\n");
    printf("2. Print NaryTree\n");
    printf("3. Exit");
    printf("\nEnter your choice: ");
    scanf("%d", &*choice);
}

所有代码(除了主代码)都取自这里 --> CLICK HERE

我们将不胜感激每一个帮助或建议。在此先感谢:)

【问题讨论】:

    标签: c tree children appendchild


    【解决方案1】:

    您的错误在于节点的初始化:您没有为数据分配内存缓冲区。你让它指向你的参数,即在堆栈上而不是在堆上。一旦你的createNodefunction 结束,堆栈就会被清空,你的参数(所以你的数据值)就会丢失。

    NaryTree *createNode ( int children , int *data) { 
        // Allocate space for a new NaryNode in memory
        NaryNode *node = (NaryNode*) calloc (1 , sizeof (NaryNode) );
    
        // Set the contents of the NaryNode appropriately
        // node->data = data; 
        node->data = malloc(sizeof(node->data));
        *node->data = *data;
        node->n = children ; 
        node->child = (NaryNode**) calloc ( children , sizeof (NaryNode*) );
    
        // Return the node we initialized
        return node;
    }
    

    或者,更简单:

    typedef struct sNaryNode { 
         // int *data; // Point to the node ’s data
         int data; // contains the node ’s data
         int n; // The number of children 
         struct sNaryNode **child; // The child list
    } NaryNode;
    

    并直接将 int 数据而不是指针传递给createNode

    NaryTree *createNode ( int children , int data) { 
        // Allocate space for a new NaryNode in memory
        NaryNode *node = (NaryNode*) calloc (1 , sizeof (NaryNode) );
    
        // Set the contents of the NaryNode appropriately
        // node->data = data; 
        node->n = children ; 
        node->child = (NaryNode**) calloc ( children , sizeof (NaryNode*) );
    
        // Return the node we initialized
        return node;
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-12-31
      • 1970-01-01
      • 1970-01-01
      • 2010-11-24
      • 1970-01-01
      • 2016-07-30
      • 2013-01-28
      相关资源
      最近更新 更多