I'm doing a program that reads records and saves these records in a linked list and in a binary tree.
However, I am not able to save the nodes in the binary tree, appearing a segment fault error.
I'd like to know why this error appears and how to fix it.
Here is my main.c file:
int main(){
registro p1_main;
lista p2_main;
nodo p3_main;
int escolha1 = 99, escolha2;
criarLista(&p2_main);
cria_arvore(&p3_main);
do {
printf("Qual opção a seguir você deseja realizar?\n\n1-Adicionar Contato\n2-Apresentar nomes registrados\n\n");
scanf("%d", &escolha1);
switch(escolha1){
case 1:
criar_registro(&p1_main);
insere_ini(&p2_main, &p1_main);
CriarNodo(&p1_main);
insere_Arvore(&p3_main, &p1_main);
case 2:
imprime_nomes(&p2_main);
}
}
while ( escolha1 != 0);
return 0;
}
Here is the structure.h of the codes:
#include <stdio.h>
#include <stdlib.h>
typedef struct registro_st{ // sequência de objetos do mesmo tipo
char login[50];
char nome[50];
float valor;
} registro;
typedef struct nodo_st{
registro *dado;
struct nodo_st *dir;
struct nodo_st *esq;
} nodo;
typedef struct Lista_st{
nodo *cabeca;
nodo *cauda;
int tamanho;
} lista;
nodo* CriarNodo(registro * p){
nodo* n;
n = (nodo*)malloc(sizeof(nodo));
n->dado = p;
n->dir = NULL;
n->esq = NULL;
return n;
}
void criarLista(lista *l){
l->cauda = NULL;
l->cabeca = NULL;
l->tamanho = 0;
}
void insere_ini(lista *l, registro* dado){
nodo* novo = (nodo*)malloc(sizeof(nodo));
if(novo == NULL){
return 0; //falta de espaço
};
novo->dado = dado;
novo->dir = l->cauda; //antigo primeiro aponta para o próximo
l->cauda = novo; // novo nodo recebe ponteiro para começo
l->tamanho = l->tamanho + 1;
printf("\n\nEsse foi o registro de num: %d.\n", l->tamanho);
printf("\nnodo implementado!!\n");
return novo;
}
nodo* raiz;
//FUNÇÕES PARA UTILIZAR NO MAIN
void imprime_nomes(lista *l){ // função que imprime os valores
nodo* p = l->cauda;
while(p)
{ // Usando while, não é necessário estabelecer um loop para percorrer toda lista.
printf("Login eh: %s\n", p->dado->login);
printf("Nome eh: %s\n", p->dado->nome);
p = p->dir;
}
}
void criar_registro(registro *p){ //função para adicionar os contatos
printf("Qual login para registro:\n");
scanf("%s", &p->login);
printf("Qual o nome do contato:\n");
scanf("%s", &p->nome);
printf("Qual valor para registrar:\n");
scanf("%f", &p->valor);
}
nodo* raiz; //porque um ponteiro para um ponteiro?
nodo* cria_arvore(){ //função para criar árvore
nodo* raiz = (nodo*)malloc(sizeof(nodo));
if(raiz != NULL)
{
return raiz;
}
}
void insere_Arvore(nodo **raiz, struct registro_st *registro)
{
//o compilador faz sempre cast de void* para o tipo indicado, não sendo assim necessário
nodo* novo = malloc(sizeof(nodo)); /*agora sem cast pois é desnecessário*/
if(novo == NULL)
{
return; /* é void logo não pode ter tipo de retorno*/
}
novo->dado = registro; //o dado é o registro todo em si
novo->dir = NULL;
novo->esq= NULL;
if(*raiz == NULL) //ver se o valor do ponteiro é null, logo arvore vazia
{
*raiz = novo;
return;
}
nodo* atual = *raiz;
nodo* ant = NULL;
while(atual != NULL) //ciclo agora só para navegar até ao sitio correto
{
ant = atual;
//o valor a ser inserido vem no próprio registro, com registro->valor
if (registro->valor == atual->dado->valor)
{
free(novo);
return; /* é void logo não pode ter tipo de retorno*/
}
if(registro->valor > atual->dado->valor)
{
atual = atual->dir;
}
else
{
atual = atual->esq;
}
}
//após navegar é feita a inserção pelo no anterior.
if (registro->valor > ant->dado->valor){ //se maior que o anterior fica a direita
ant->dir = novo;
}
else { //senão fica a esquerda
ant->esq = novo;
}
}