【问题标题】:How to fix error where a node in a tree is not being printed如何修复未打印树中节点的错误
【发布时间】:2019-11-05 09:54:13
【问题描述】:

我正在尝试将 4 个名称插入 bst。我有打印语句,说明名称在树上的哪个位置通过,然后当名称找到有效位置时输出“null”的打印语句。例如:

如果根是 Dennis,下一个要插入的节点是 Armin,则打印

左 空

但是,当我尝试按顺序打印树时,我错过了一个名称。

我尝试手动打印出节点,就像 printf("%s", node->data);但我只是得到一个分段错误。

我要打印的名字是apple、cris、dennis、loki。但输出是:apple, cris, loki。它总是跳过丹尼斯。

bstNode* insertNode(bstNode *root, char *data){

    if(root == NULL){
        printf("null, %s\n", data);

        root = newNode(data);
        return;
        }

    else if(wordSort(root->data, data) == -1){
        printf("right, %s\n", data);
        root->right = insertNode(root->right, data);
    }
    else if(wordSort(root->data, data) == 1){
        printf("left, %s\n", data);
        root->left = insertNode(root->left, data);
    }
}
  void printTree(bstNode *node){
//printf("%s\n", node->left->data);
//printf("%s\n", node->data);
//printf("%s\n", node->right->data);
//printf("%s\n", node->right->right->data);


 if (node == NULL)
          return;

     printTree(node->left);


     printf("%s\n", node->data);


     printTree(node->right);

}
bstNode* newNode(char *data){

bstNode* newnode = (bstNode*)malloc(sizeof(bstNode));
newnode->data =  (char*)malloc(100 * sizeof(char));
strcpy(newnode->data, data);
newnode->left = NULL;
newnode->right = NULL;
strcpy(newnode->data, data);
newnode->count = 1;
return newnode;
}

【问题讨论】:

  • 函数 bstNode* insertNode(bstNode *root, char *data){ 虽然返回类型为 bstNode *,但什么也不返回。
  • bstNode 严重损坏。例如,如果rootNULL,它将调用newNode,将结果分配给局部变量root,然后返回,丢弃新节点并保持调用者的根不变。它已被声明为返回 bstNode *,但已被实现为(有缺陷的)void 函数。需要修复它以始终返回新的根节点。
  • 我目前正在 PuTTY 上运行程序,这就是代码出现故障的地方,但是当我将相同的代码插入在线编译器时,它可以完美运行。任何原因以及无论如何我都可以在 PuTTY 上修复它
  • 它可能起作用的唯一方法是调用者碰巧从寄存器中提取了一个杂散值(例如root),这实际上是正确的返回值。但是你不能依赖这个。这也是一个毫无意义的错误 - 只需修复它。您的编译器应该对此代码给出多个警告。在寻求帮助之前,请务必修复警告。
  • 没关系,我明白你的意思,汤姆。我修复了它,它现在可以工作了,非常感谢:)

标签: c recursion memory-management binary-search-tree undefined-behavior


【解决方案1】:

函数insertNode 具有未定义的行为,因为尽管返回类型为bstNode *,但它什么也不返回。

如演示程序所示,可以通过以下方式定义和调用。

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

typedef struct bstNode
{
    char *data;
    struct bstNode *left;
    struct bstNode *right;
} bstNode;

bstNode * newNode( const char *data )
{
    bstNode *node = malloc( sizeof( bstNode ) );

    if ( node != NULL )
    {
        node->left  = NULL;
        node->right = NULL;

        size_t n = strlen( data );
        node->data = malloc( n + 1 );

        if ( node->data != NULL )
        {
            strcpy( node->data, data );
        }
        else
        {
            free( node );
        }
    }

    return node;
}

bstNode * insertNode( bstNode *root, const char *data )
{
    if ( root == NULL )
    {
        root = newNode( data );
    }
    else if ( strcmp( root->data, data ) < 0 )
    {
        root->left = insertNode( root->left, data );
    }
    else
    {
        root->right = insertNode( root->right, data );
    }

    return root;
}

void printTree( const bstNode *root )
{
    if ( root != NULL )
    {
        printTree( root->left );
        puts( root->data );
        printTree( root->right );
    }
}
int main(void) 
{
    bstNode *root = NULL;

    root = insertNode( root, "pple" );
    root = insertNode( root, "cris" );
    root = insertNode( root, "dennis" );
    root = insertNode( root, "lok" );

    printTree( root );

    return 0;
}

程序输出是

pple
lok
dennis
cris

【讨论】:

    【解决方案2】:

    错误在于你的逻辑。请确保您很好地理解递归。 例如,在下面的语句中,您将 root->right 指向任何内容,因为 insertNode(root->right, data) 语句执行时它进入第一个 if 块,然后由于 root 为空,它使用给定数据创建一个节点但不返回任何节点。

    root-&gt;right = insertNode(root-&gt;right, data);

    这就是您的程序出现分段错误的原因。您的程序正在做的是创建节点但不链接节点。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2019-05-24
      • 2018-12-17
      • 1970-01-01
      • 1970-01-01
      • 2012-04-15
      • 2020-01-11
      • 2018-10-12
      相关资源
      最近更新 更多