使用scanf()输入字符的问题

我正在尝试将一个角色输入一个链接列表,其中角色可以是’A’,’a’,’G’,’g’,’T’,’t’,’C’或’c’。

我还不熟悉C,我知道我搞砸了一些东西:

do{ printf ("\nEnter a new nucleotide: \n"); scanf("%c",&newChar); /* Checking */ if(newChar == 'A' || newChar == 'a' || newChar == 'G' || newChar == 'g' || newChar == 'T' || newChar == 't' || newChar == 'C' || newChar == 'c' ) { AddToSequence(newChar); size++; } else { printf ("\nBad Element"); } }while(newChar != 'x'); 

newChar初始化为垃圾值,在本例中为“q”。

输入’x’退出循环,输入任何可接受的值调用AddToSequence(),任何不可接受的值都会收到警告。

出于某种原因,无论newChar中有什么价值,它都会跳转到其他地方。 它也会直接跳过scanf,无需等待用户输入,每次循环时都会执行两次循环。 谁能告诉我哪里出错了?

完整计划:

 #include #include /*Structure declaration for the node*/ struct node{ char nucleotide; struct node *point; }*start; /* Adds a nucleotide to the chain. Creates a new linked list if no chain exists exists.*/ void AddToSequence(char nucleotide){ struct node *loc, *first; //Dynamic memory is been allocated for a node first=(struct node*)malloc(sizeof(struct node)); first->nucleotide=nucleotide; first->point=NULL; if(start==NULL){ /*If list is empty*/ start=first; }else{ /*Element inserted at the end*/ loc=start; while(loc->point!=NULL){ loc=loc->point; loc->point=first; } } } /* Display elements */ void Display(){ struct node *loc; if(start == NULL){ printf ("\n\nList is empty"); return; } loc=start; printf("\n\nList is : "); while(loc!=NULL){ printf ("%c", loc->nucleotide); loc=loc->point; } printf ("\n"); } /* Finds and displays percentage of the chain made up of each nucleotide. */ void Percentage(int size){ struct node *loc; if(start == NULL){ printf ("\n\nList is empty"); return; } loc=start; printf("\n\nList is : "); int A = 0, G =0, T =0, C = 0; double Adouble = 0, Gdouble =0, Tdouble=0, Cdouble=0; while(loc!=NULL){ if(loc->nucleotide=='A' || 'a'){A++;} if(loc->nucleotide=='G' || 'g'){G++;} if(loc->nucleotide=='T' || 't'){T++;} if(loc->nucleotide=='C' || 'c'){C++;} loc=loc->point; } printf ("\n"); /* Convert to double for percentages as int loses precision */ Adouble =A; Gdouble =G; Tdouble =T; Cdouble =C; Adouble =(Adouble/size)*100; Gdouble =(Gdouble/size)*100; Tdouble =(Tdouble/size)*100; Cdouble =(Cdouble/size)*100; printf("\nA: %f", Adouble); printf("\nG: %f", Gdouble); printf("\nT: %f", Tdouble); printf("\nC: %f", Cdouble); } /* There be dragons beyond here */ int main(){ int navigate, size =0; char newChar = 'q'; do{ /* Menu */ printf("\n 1. Create / Extend Sequence\n"); printf("\n 2. Display Sequence\n"); printf("\n 3. Count \n"); printf("\n 0. Exit \n"); printf("\nPlease select an option (0 to 3)\n"); scanf("%d",&navigate); switch (navigate){ case 0: /* Exit */ break; case 1: /* Add nucleotides */ do{ printf ("\nEnter a new nucleotide: \n"); scanf("%c",&newChar); /* Some error checking */ if(newChar == 'A' || newChar == 'a' || newChar == 'G' || newChar == 'g' || newChar == 'T' || newChar == 't' || newChar == 'C' || newChar == 'c' ){ AddToSequence(newChar); size++; } else { printf ("\nBad Element"); } }while(newChar != 'x'); break; case 2: Display(); break; case 3: Percentage(size); break; default: printf ("\n\nBad choice. Please select another.\n"); } } while (navigate !=0); return 0 ; } 

您不处理换行符。 %c说明符不会跳过空格。 尝试:

 scanf(" %c", &newChar); /* ^ <-- Makes `scanf` eat the newline. */ 

或者可以添加一个明确的测试。

 scanf(...); if (newChar == '\n') continue; 

"%c"添加空格以捕获换行符。 space charcter用于捕获空格字符,制表符,换行符

 scanf("%c ",&newChar); 

你在stdin上留下'\n'

 scanf("%d",&navigate); getchar(); // consume the newline character ... scanf("%c",&newChar); getchar(); // consume the newline character 

或者既然你已经在使用scanf()你可以告诉scanf本身来处理换行符:

 scanf("%d\n", &navigate); .... scanf("%c\n",&newChar); 

更好的是你可以通过在格式特定之后添加一个空格来打开它:

 scanf("%d ", &navigate); .... scanf("%c ",&newChar); 

以防用户想要执行以下操作: 2

无论你如何处理它,关键是你需要使用换行符。

使用

 newChar=getche(); 

这是一个非标准函数,它从键盘获取一个字符,回显到屏幕。