Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/55.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
尝试打印到文件时,C中出现分段错误_C_Segmentation Fault_Binary Tree - Fatal编程技术网

尝试打印到文件时,C中出现分段错误

尝试打印到文件时,C中出现分段错误,c,segmentation-fault,binary-tree,C,Segmentation Fault,Binary Tree,我创建了一个函数,该函数应该在参数中获取一个二叉树,在用户输入中获取一个文件名,并在该文件中打印二叉树,以便稍后通过graphviz转换为图片 提供的二叉树类型为: struct noeud_s; typedef struct noeud_s noeud; typedef noeud* arbre; struct noeud_s{ char* valeur; arbre gauche; arbre droit; }; 我创建的两个功能是: void create_dot(ar

我创建了一个函数,该函数应该在参数中获取一个二叉树,在用户输入中获取一个文件名,并在该文件中打印二叉树,以便稍后通过graphviz转换为图片

提供的二叉树类型为:

struct noeud_s;

typedef struct noeud_s noeud;

typedef noeud* arbre;

struct noeud_s{
  char* valeur;
  arbre gauche;
  arbre droit;
};
我创建的两个功能是:

void create_dot(arbre racine)
{
  FILE *f;
  char file_name[100];
  printf ("Nom du fichier a creer (Ajouter .dot a la fin): ");
  scanf ("%s", file_name);
  printf("Name: %s\n", file_name);
  printf ("Creation du fichier dot\n");
  f = fopen(file_name, "w");
  if (f == NULL)
  {
    printf("NULL\n");
  }
  fprintf(f, "digigraph tree {\n");
  write_to_dot(f, racine);
  fprintf(f, "}");
  fclose(f);
}

void write_to_dot(FILE *f, arbre racine)
{
  if (racine == NULL)
  {
    return;
  }
  if (racine != NULL)
  {
    fprintf(f, "%s -> %s [label = \"non\"]\n", racine -> valeur, racine -> gauche -> valeur);
    fprintf(f, "%s -> %s [label = \"oui\"]\n", racine -> valeur, racine -> droit -> valeur);
    write_to_dot(f, racine -> gauche);
    write_to_dot(f, racine -> droit);
  }
  return;
}

就调试而言,我推断我的分段错误发生在write_to_dot函数中。但是因为我不能正确处理gdb,我希望你能帮我找到我的分段错误并解释一下。

代码正在打印出一个二叉树。没有代码显示节点是如何构造的,但在典型的二叉树中,叶节点具有
NULL
左和右子节点(或
gauche
droit

函数
write_to_dot
将在第一个叶节点(如果不是在中间分支节点的空侧)失败,因为
racine->gauche
racine->droit
将为
NULL
,但它们仍然被取消引用-
racine->gauche->valeur
,而不进行任何检查

虽然我没有所有的代码,但至少测试这种情况可以解决其中一个问题:

void write_to_dot ( FILE *f, arbre racine )
{
    if ( racine != NULL )
    {
        if (racine->gauche != NULL)
            fprintf ( f, "%s -> %s [label = \"non\"]\n", racine->valeur, racine->gauche->valeur );
        else
            fprintf ( f, "%s -> NULL [label = \"non\"]\n", racine->valeur );

        if (racine->droit != NULL)
            fprintf ( f, "%s -> %s [label = \"oui\"]\n", racine->valeur, racine->droit->valeur );
        else
            fprintf ( f, "%s -> NULL [label = \"oui\"]\n", racine->valeur );

        write_to_dot ( f, racine->gauche );
        write_to_dot ( f, racine->droit );
    }
}

您正在此处解除对空指针的引用:
fprintf(f),%s->%s[label=\“non\”]\n,racine->valeur,racine->gauche->valeur)-->
fprintf,“%s->%s[label=\“non\”]\n”,racine->valeur,rachine->gauche?racine->gauche->valeur:“Jamais!”;
如果你可以在
gdb
下运行你的程序,你可以输入像
print racine
print racine->valeur
print racine->gauche
这样的命令。这很可能会很快找出问题所在。我们不能这样做,因为我们不知道你的代码是如何调用
create\u dot
。很可能问题在于为
racine
传递的值以及它所指向的内容。“但是因为我不能正确处理gdb”-那么这将是一个极好的机会让你学习如何正确处理gdb。”教一个人钓鱼“还有那些东西。如果可以的话,
typedef noeud*arbre。。。我想建议,将指针类型定义为另一个名称只会使事情变得混乱。当然,除非“arbre”只是指“指向”@Kingsley,否则我知道这很混乱,但我别无选择。我把它作为一个类型定义,我不能改变它