2013-08-16 7 views
0

Кто-нибудь знает, что может быть проблемой при использовании следующего кода? Когда я бегу, я получаю следующий результат:Связанный список проблем

Insert a value in the list: 1 
Do you want to continue? y/N: 
1 -> 

Дело в том, что цикл делать-то время не выполняет до scanf("%c", &ch) заявления, а затем выпрыгивает (так что я не могу представить какой-либо вход для переменной ch) , Я пытался отладки с помощью GDB, и я получил некоторые странные сообщения:

GI___libc_malloc (bytes=16) at malloc.c:malloc.c: No such file or directory. 

Кроме того, он говорит, что компилятор не может найти файл vscanf.c. Кто-нибудь объясняет это странное поведение? Благодаря! (Намерение напечатать значения однократно связанный список в обратном порядке.)

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

struct node{ 
    int info; 
    struct node* next; 
}; 

struct node* head = 0; 

void add_node(int value){ 

    struct node* current = malloc(sizeof(struct node)); 
    current->info = value; 
    current->next = head; 
    head = current; 
} 

void print_node(struct node* head){ 

    while(head){ 

      printf(" %d -> ", head->info); 
      head = head->next; 
    } 

    printf("\n"); 
} 

int main(void){ 

    int val; 
    char ch; 

    do { 

     printf("Insert a value in the list: "); 
     scanf("%d", &val); 
     add_node(val); 
     printf("Do you want to continue? y/N: "); 
     scanf("%c", &ch); 

    } while(ch == 'y' || ch == 'Y'); 

    printf("\n"); 
    print_node(head); 
    return 0; 
} 
+0

Полный выстрел в темноте здесь, может ли второе сканирование читать в новой строке? –

+0

изменить метод подписи add_node, чтобы принять параметр struct node *, а затем передать адрес головы в качестве аргумента для вызова функции. Это должно сделать это. – Clocks

+0

Сообщения GDB служат для информирования вас о том, что вы не можете входить в файлы GLIB, просто нажмите c, чтобы продолжить. – Clocks

ответ

0

Проблема, с которой вы сталкиваетесь, заключается в том, что после ввода значения для val и затем нажмите enter, то \n все еще остается во входном буфере. Следовательно, следующий scanf предполагает, что \n, который по-прежнему находится во входном буфере, является его входом и потребляет его, а затем выходы цикла.

Другие решения: -

1) scanf("%d%*c",&val);

Это присвоит первый входной символ val, а затем что-нибудь после того, что будет съедено. Следовательно, \n не пошел бы в следующий scanf

2) scanf("%[^\n]%*c",&val);

Это присвоит что-нибудь к val кроме \n, а затем \n будет съедена.

2

Если вы хотите, чтобы вход отделяться новой линией (который он кажется, что вы делаете), а затем изменить формат как вы читаете в своем персонаже. Изменение следующее:

scanf("%c", &ch); 

... к этому:

scanf("\n%c", &ch); // << Note, \n to pickup newline before reading the value. 
+0

Если бы это была проблема, не мог ли он просто выполнить 'scanf («% d \ n », &val);' вместо того, чтобы делать два 'scanf's? –

+0

Когда вы выполняете' scanf ("% d \ n", &val); ', программа ждет чего-то другого, кроме ввода, и она просто печатает и завершает работу после того, как вы что-то ввели. – sha1

+0

@ Jacob, я получил идею использования' '\ n'', спасибо.Но, поскольку я знаю, что 'scanf()' игнорирует символ '\ n''. Я ошибаюсь? – sha1

2

Вы можете проверить правильность ввода в если-иначе блок, и выполнить свой код соответственно. Например, вот что я буду делать, если мне нужно, чтобы проверить, хочет ли пользователь продолжать или нет:

char chTemp; //Declare a test variable to check for newline 
printf("Do you want to continue? y/N: "); 
if (scanf("%c%c",&ch,&chTemp) != 2 || chTemp != '\n') 
{ 
    printf("Error in input (Integer input provided)"); 
} 
else 
{ 
    //Do stuff. 
} 

Не только он будет решить вашу проблему, но она также будет проверять нерадивых целочисленных входов.

Смежные вопросы