2016-11-14 9 views
-1

私はC言語を新しくしていますが、ポインタや好きなリストの仕組みを理解するのにはまだ苦労しています。Cを再帰的にリンクリストからノードを削除する

リンクリストからノードを削除しようとしていますが、this linkの例を使用していますが、動作させることができません。

ここに私のコードです:

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

typedef struct voos 
{ 
int numeroVoo; 
char ciaAerea[20]; 
char modeloAeronave[20]; 
char origem[20]; 
char destino[20]; 
int qtdeTotalAssentos; 
int qtdeAssentosOcupados; 
struct voos *proximo; 
} *cadastroVoo; 

int cont = 0; //Contador temporario para contar numero de assentos ocupados 
void addVoo (cadastroVoo *local) //Add item to list 
{ 
cadastroVoo novo; 
novo = (cadastroVoo) malloc(sizeof(struct voos)); 
char temp[20]; 
if (novo != NULL) 
{ 
    printf("Informe o numero do voo: \n"); 
    scanf("%d", &novo->numeroVoo); 

    printf("Informe a cia aerea: \n"); 
    fflush(stdin); 
    gets(temp); 
    strcpy(novo->ciaAerea, temp); 

    printf("Informe o modelo da aeronave: \n"); 
    fflush(stdin); 
    gets(temp); 
    strcpy(novo->modeloAeronave, temp); 

    printf("Informe a origem do voo: \n"); 
    fflush(stdin); 
    gets(temp); 
    strcpy(novo->origem, temp); 

    printf("Informe o destino do voo: \n"); 
    fflush(stdin); 
    gets(temp); 
    strcpy(novo->destino, temp); 

    cont++; 
    novo->qtdeAssentosOcupados = cont; 

    novo->qtdeTotalAssentos = 50; 

    novo->proximo = *local; 
    *local = novo; 
} 
} 

void listarVoos(cadastroVoo local) //prints list 
{ 
printf("Imprimindo lista atualizada: \n\n\n"); 
while (local != NULL) 
{ 
    printf("Numero voo: %d\n", local->numeroVoo); 
    printf("Cia Aerea: %s\n", local->ciaAerea); 
    printf("Modelo aeronave: %s\n", local->modeloAeronave); 
    printf("Origem: %s\n", local->origem); 
    printf("Destino: %s\n", local->destino); 
    printf("Quantidade total de assentos: %d\n", local->qtdeTotalAssentos); 
    printf("Quantidade de assentos ocupados: %d\n", local->qtdeAssentosOcupados); 
    printf("\n"); 
    local = local->proximo; 
} 
} 

cadastroVoo *cancelarPassagem(cadastroVoo *local, int numVoo) //deletes item from list 
{ 
// See if we are at end of list. 
if (local == NULL) return NULL; 

// Check to see if current node is one to be deleted. 
if (local->numeroVoo == numVoo) 
{ 
    cadastroVoo *tempNextP; 

    tempNextP = local->proximo; 

    free(local); 

    return tempNextP; 
} 

// Check the rest of the list, fixing the next pointer in case the next node is the one removed. 
local->proximo = cancelarPassagem(local->proximo, numVoo); 

//Return the pointer to where we were called from. Since we did not remove this node it will be the same. 
return local; 
} 

int main() 
{ 
cadastroVoo cadastro = NULL; 
char op; 
while(op != 'f') 
{ 
    printf("Escolha a opcao:\n"); 
    printf("a - Incluir voos:\n"); 
    printf("b - Listar voos:\n"); 
    printf("c - Reservar assento em um voo:\n"); 
    printf("d - Cancelar voo:\n"); 
    printf("e - Cancelar passagem:\n"); 
    printf("f - Sair:\n"); 
    op = getche(); 
    printf("\n"); 
    switch(op) 
    { 
    case 'a': 
     { 
      printf("Incluir voo. \n"); 
      addVoo(&cadastro); 
      printf("Voo incluso.\n"); 
      break; 
     } 
    case 'b': 
     { 
      listarVoos(cadastro); 
      break; 
     } 
    case 'c': 
     { 
      printf("Reservar assento em um voo. \n"); 
      addVoo(&cadastro); 
      printf("Assento reservado.\n"); 
      break; 
     } 
    case 'd': 
     { 
      /** 
      *while (cancelarVoo != NULL) cancelarVoo() 
      */ 
      break; 
     } 
    case 'e': 
     { 
      int numVoo; 
      printf("Informe o numero do voo que deseja cancelar a passagem: \n"); 
      scanf("%d", &numVoo); 
      cancelarPassagem(&cadastro, numVoo); 
      printf("Passagem cancelada"); 
      break; 
     } 
    case 'f': break; 
    default: 
     { 
      printf("Opcao invalida."); 
      break; 
     } 
    } 
} 

return 0; 
} 

メソッド宣言では、私が合格した場合:

cadastroVoo *cancelarPassagem(cadastroVoo *local, int numVoo) 

を私はエラーを取得:メンバーのリクエスト「numeroVoo」何かない構造体または共用

しかし、合格すれば

cadastroVoo *cancelarPassagem(cadastroVoo local, int numVoo) 

これは実行されますが、このメソッドを呼び出すオプションを選択すると、動作しなくなったウィンドウでメッセージが表示されます。

誰かが間違っている可能性があることを知っていますか?

ありがとうございます。

+0

リンクを含めないでください。リストがどのように定義されているかをここに示します。 –

+0

'cadastroVoo'は既にポインタでなければなりません。さて、あなたの警告を確認してください。あなたの変更には戻り値の型も含める必要があり、変更されなかったからです。また、あなたのリストとその定義をどのように配分するかを示す必要があります。 –

+0

コンパイルで4つの警告と4つのエラーが生成されました。 –

答えて

0

です。私はここであなたのコードを試して、ロジックは正常に動作しています。

#include <stdio.h> 
typedef struct cadastroVoo { 
    struct cadastroVoo *proximo; 
    int numero; 
} CadastroVoo; 

CadastroVoo *cancelarPassagem(CadastroVoo *local, int num); 

void inserir(CadastroVoo *cabeca, int num) { 
    CadastroVoo *p = (CadastroVoo *) malloc(sizeof(CadastroVoo)); 
    p->proximo = cabeca->proximo; 
    p->numero = num; 
    cabeca->proximo = p; 
} 

CadastroVoo *cancelarPassagem(CadastroVoo *local, int num) { 
    if (local == NULL) return NULL; 
    printf("> %d\n", local->numero); 
    printf("> %p\n", local->proximo); 
    if (local->numero == num) { 
     CadastroVoo *proximo = local->proximo; 
     free(local); 
     return proximo; 
    } 
    local->proximo = cancelarPassagem(local->proximo, num); 
    return local; 
} 

int main() { 
    CadastroVoo *cabeca = (CadastroVoo *) malloc(sizeof(CadastroVoo)); 
    cabeca->proximo = NULL; 

    inserir(cabeca, 10); 
    inserir(cabeca, 20); 
    inserir(cabeca, 30); 
    inserir(cabeca, 40); 
    inserir(cabeca, 50); 

    cancelarPassagem(cabeca->proximo, 20); 

    CadastroVoo *p = cabeca->proximo; 
    while (p != NULL) { 
     printf("%d\n", p->numero); 
     p = p->proximo; 
    } 
} 
0

質問に実際のコードの代わりに参照を付けることは悪い考えです。

ただし、ここでは、単一リンクリストを持つ再帰メソッドを使用する簡略化されたデモンストレーションプログラムを示します。私はそれがあなたが必要とすることを行うと確信しています。それを調査し、それに応じてプロジェクトを変更してください。

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

typedef struct List 
{ 
    int data; 
    struct List *next; 
} List; 

List * add_node(List *head, int data) 
{ 
    if (head == NULL) 
    { 
     head = malloc(sizeof(List)); 
     head->data = data; 
     head->next = NULL; 
    } 
    else 
    { 
     head->next = add_node(head->next, data); 
    } 

    return head; 
} 

List * remove_node(List *head, int data) 
{ 
    if (head != NULL) 
    { 
     if (head->data == data) 
     { 
      List *tmp = head; 
      head = head->next; 
      free(tmp); 
     } 
     else 
     { 
      head->next = remove_node(head->next, data); 
     } 
    } 

    return head; 
} 

void display_list(List *head) 
{ 
    if (head != NULL) 
    { 
     printf("%d ", head->data); 
     display_list(head->next); 
    } 
} 

int main(void) 
{ 
    const int N = 10; 
    List *head = NULL; 

    for (int i = 0; i < N; i++) 
    { 
     head = add_node(head, i); 
     display_list(head); 
     printf("\n"); 
    } 

    for (int i = N; i != 0; i--) 
    { 
     head = remove_node(head, i - 1); 
     display_list(head); 
     printf("\n"); 
    } 

    return 0; 
} 

プログラムの出力は、おそらくあなたが関数へのポインタを渡していません

0 
0 1 
0 1 2 
0 1 2 3 
0 1 2 3 4 
0 1 2 3 4 5 
0 1 2 3 4 5 6 
0 1 2 3 4 5 6 7 
0 1 2 3 4 5 6 7 8 
0 1 2 3 4 5 6 7 8 9 
0 1 2 3 4 5 6 7 8 
0 1 2 3 4 5 6 7 
0 1 2 3 4 5 6 
0 1 2 3 4 5 
0 1 2 3 4 
0 1 2 3 
0 1 2 
0 1 
0 
関連する問題