This is the problem I'm trying to solve:
Input:
First line contains N, the size of the string.
Second line contains the letters (only lowercase).
Output:
Print YES if all vowels are found in the string, NO otherwise.
Constraints:
The size of the string will not be greater than 10,000. 1 ≤ N ≤ 10000
The following code I wrote is always showing NO.
#include <stdio.h>
#include<conio.h>
int main()
{
int a,b,c=0,d=0,e=0,f=0,g=0,i;
char string[10000];
scanf("%d",&a);
scanf("%s",string);
for(i=0;i<a;a++)
{
if(string[i]==('a'))
c=1;
if(string[i]==('e'))
d=1;
if(string[i]==('i'))
e=1;
if(string[i]==('o'))
f=1;
if(string[i]==('u'))
g=1;
}
if((c==1)&&(d==1)&&(e==1)&&(f==1)&&(g==1))
printf("YES");
else
printf("NO");
return 0;
getch ();
}
Here is an infinite loop that causes a problem:
for(i=0;i<a;a++)
You should increment i, instead of a (length of a string). If you fix this one char in loop statement, the program will run well at all. Anyway, I changed your code a bit to be more readable. Take a look if you want, just for your information, sir:
#include <stdio.h>
#include <stdlib.h>
int main()
{
int len, a=0, e=0, i=0, o=0, u=0, it;
char string[10000];
scanf("%d", &len);
scanf("%s", string);
for(it=0;it<len;it++)
{
if(string[it]=='a') a = 1;
else if(string[it]=='e') e = 1;
else if(string[it]=='i') i = 1;
else if(string[it]=='o') o = 1;
else if(string[it]=='u') u = 1;
}
if(a && e && i && o && u) printf("YES\n");
else printf("NO\n");
system("PAUSE");
return 0;
}
I assume you are running your program under Windows, so instead of conio's getch() try to use system("PAUSE") or just even better way to do this (for both Windows for UNIX): getchar()
I've renamed all of your variables, but otherwise left the code the same.
#include <stdio.h>
#include<conio.h>
int main()
{
int foundA = 0, foundE = 0, foundI = 0, foundO = 0, foundU = 0;
int i, length;
char string[10000];
scanf("%d", &length);
scanf("%s", string);
for(i=0; i<length; length++)
{
if(string[i]==('a'))
foundA=1;
else if(string[i]==('e'))
foundE=1;
else if(string[i]==('i'))
foundI=1;
else if(string[i]==('o'))
foundO=1;
else if(string[i]==('u'))
foundU=1;
}
if((foundA==1)&&(foundE==1)&&(foundI==1)&&(foundO==1)&&(foundU==1))
printf("YES");
else
printf("NO");
return 0;
getch ();
}
Looking the the for-loop condition for(i=0; i<length; length++), I think it's pretty clear what's wrong. Instead of incrementing the counter, you're incrementing the length of the string. Eventually, the counter overflows to a negative number, and the loop terminates without ever looking at a character besides the first one. The lesson here is to name your variables properly.
If you want to be picky, then signed integer overflow is undefined behavior, but for most systems, INT_MAX + 1 will be INT_MIN.
This program can be done in more simpler way other as below.
#include <stdio.h>
#include<conio.h>
int main()
{
int i, flag = 0;
char string[10000], *ptr;
char cmp[] = "aeiou";
printf("Please enter string = " );
scanf("%s", string);
i = 0;
while(cmp[i])
{
ptr = string;
while(*ptr)
{
if(cmp[i] == *ptr)
break;
ptr++;
}
if(*ptr != cmp[i++])
{
flag = 1;
break;
}
}
if(flag == 1)
printf("NO");
else
printf("YES");
}
In this program I have used just one flag instead of 5 flags. Always try to write simple code rather then using unnecessary variable and flags.
Related
I wrote two sample programs to check for a palindrome string. But in both I am getting output like, its not a palindrome number. What I am missing?
I strictly assume somehow code is executing my if statement and put flag in to 1. May be because of that length calculation. Anyone has a better idea?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <conio.h>
int main(void) {
setbuf(stdout,NULL);
char name[100];
int i,length,flag=0,k;
printf("Enter your name");
/*scanf("%s",name);*/
gets(name);
length=strlen(name);
for(i=0;i<=length-1;i++)
{
for(k=length-1;k>=0;k--)
{
if(name[i]!=name[k])
{
flag=1;
break;
}
}
}
if(flag==0)
{
printf("Give word is a palindrome");
}
if(flag==1)
{
printf("This is NOT a palindrome word");
}
return 0;
}
and
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <conio.h>
int main(void) {
setbuf(stdout,NULL);
char name[100];
int i,length,flag=0;
printf("Enter your name");
/*scanf("%s",name);*/
gets(name);
length=strlen(name);
for(i=0;i<=length/2;i++)
{
if(name[i]!=name[length-1])
{
flag=1;
}
}
if(flag==0)
{
printf("Give word is a palindrome");
}
if(flag==1)
{
printf("This is NOT a palindrome word");
}
return 0;
}
First Algorithm
The algorithm you are using in the first program involves comparing each letter to every other letter which does not help in determining if the number is a palindrome and it does not seem fixable.
Second Algorithm
The problem with the second approach, however, is you are always comparing name[i] to name[length]. Instead change it to length-i-1. This will start comparing from length-1 and decrement the length of the character by 1 for every next iteration:
for(i = 0;i <= length / 2;i++)
{
if(name[i] != name[length-i-1])
{
flag=1;
break;
}
}
gets() and buffer overflow
Do not use gets. This method is susceptible to a buffer overflow. If you enter a string longer than 100 characters, it will result in undefined behavior. Use fgets instead for deterministic behavior:
fgets(name, sizeof(name), stdin);
This takes in the size of the buffer and only reads up to sizeof(name) characters.
Full code
Ideally, you should consider wrapping the logic to check if the string is a palindrome in a function:
int is_palindrome(char*);
int main(void)
{
char name[100];
setbuf(stdout,NULL);
printf("Enter your name");
fgets(name, sizeof(name), stdin);
if(is_palindrome(name))
{
printf("The given word is a palindrome");
}
else
{
printf("This is NOT a palindrome word");
}
return 0;
}
int is_palindrome(char* name)
{
int length = strlen(name);
int flag = 0, i;
for(i = 0;i <= length / 2; i++)
{
if(name[i]!=name[length-i-1])
{
return 0;
}
}
return 1;
}
There is plenty wrong with both your attempts. I strongly suggest using a debugger to investigate how your code works (or doesn't).
Your first attempt performs length2 (incorrect) comparisons, when clearly only length / 2 comparisons are required. The second performs length / 2 comparisons but the comparison is incorrect:
name[i] != name[length-1] ;
should be:
name[i] != name[length - i - 1] ;
Finally you iterate exhaustively when you could terminate the comparison as soon as you know they are not palindromic (on first mismatch).
There may be other errors - to be honest I did not look further than the obvious, because there is a better solution.
Suggest:
#include <stdbool.h>
#include <string.h>
bool isPalindrome( const char* str )
{
bool is_palindrome = true ;
size_t rev = strlen( str ) - 1 ;
size_t fwd = 0 ;
while( is_palindrome && fwd < rev )
{
is_palindrome = (str[fwd] == str[rev]) ;
fwd++ ;
rev-- ;
}
return is_palindrome ;
}
In use:
int main()
{
const char* test[] = { "xyyx", "xyayx", "xyxy", "xyaxy" } ;
for( size_t t = 0; t < sizeof(test)/sizeof(*test); t++ )
{
printf("%s : %s palindrome\n", test[t],
isPalindrome( test[t] ) ? "Is" : "Is not" ) ;
}
return 0;
}
Output:
xyyx : Is palindrome
xyayx : Is palindrome
xyxy : Is not palindrome
xyaxy : Is not palindrome
Try this
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main() {
char text[100];
int begin, middle, end, length = 0;
printf("enter the name: ");
scanf("%s",text);
while ( text[length] != '\0' ){
length++;}
end = length - 1;
middle = length/2;
for ( begin = 0 ; begin < middle ; begin++ ) {
if ( text[begin] != text[end] ) {
printf("Not a palindrome.\n");
break;
}
end--;
}
if( begin == middle )
printf("Palindrome.\n");
return 0;
}
The problem with the first piece of code is you are comparing it more than required, compare it with length-i-1.
The main problem with the second code is you are comparing it with only the last letter of a word.
Hope you understood your mistake
This question already has answers here:
Why is scanf() causing infinite loop in this code?
(16 answers)
Closed 6 years ago.
I have written some C code where you can pick from an answer by inputting a 1 or 2, and if you input a higher number it will bring you back to pick another number just fine. However, if I try to input something that's not a value or a number, like a string or character, the error message at the bottom will repeat infinitely. How can I make my code act the same as if you input a higher number than 1 or 2 when you input any other character? Here the code I use abstracted:
#include <stdio.h>
int a;
int main(){
b:scanf("%d", &a);
if(a==1)
{
a=0;
}
if(a==2)
{
a=0;
}
else
{
a=0;
printf("\nERROR: Please try again.\n\n");
goto b;
}
}
EDIT: Apparently the return value is still stuck in scanf() when it returns to it. How can I clear out scanf() of its return value?
Don't use gotos at all. Instead use while loops:
#include <stdio.h>
int main(void) {
int a, end = 1; //end determines if the loop should end
do { //a do-while loop - it's the same as a while loop, except it runs atleast once
scanf("%d", &a);
switch (a) { //switches the value of a
case 1:
case 2: printf("You entered %d\n", a);
end = 0; //sets end to 0, which will end the loop(see below)
break;
default: printf("\nERROR: Please try again.\n\n");
}
} while (end); //every non-zero value is true, so when I set end to 0, it will end the loop
return 0; //don't forget the return 0: it shows you that your program ran without error
}
So I wrote it that it ends as soon as you type a valid input. You also don't need to set a to zero, as you read it in again every time you run the loop.
EDIT: if you want to check for invalid input such as 5x, you can use the following:
int check, var, error;
char ch;
do {
error = 0;
check = scanf("%d%c", &var, &ch);
if (check != 2 || ch != '\n') {
printf("Wrong input. Try again -> ");
error = 1;
fflush(stdin);
}
} while (error);
#include <stdio.h>
int a;
int isNumeric(const char *str)
{
while(*str != '\0')
{
if(*str < '0' || *str > '9')
return 0;
str++;
}
return 1;
}
int main(){
char inputStr[10];
while(1){
scanf("%9s",inputStr);
if(!isNumeric(inputStr)){
a=0;
printf("\nERROR Not a number: Please try again.\n\n");
}else {
a = atoi(inputStr);
if(a==1){
a = 0;
}else if(a == 2){
a == 0;
}else{
a=0;
printf("\nERROR : Please try again.\n\n");
}
}`enter code here`
}
}
Have not tested. But I guess you will get a good idea. check strtol function. That is also useful.
Something like...
Note: Obviously 999 is an arbitrary value. Just chosen to give you an example.
#include <stdio.h>
int main(){
int a = 1;
while (a != 999){
scanf("%d", &a);
if(a==1)
{
a=0;
}
if(a==2)
{
a=0;
}
else if (a != 999)
{
a=0;
printf("\nERROR: Please try again.\n\n");
}
} // while()
} // main()
This is a code that has to take an input array from the user and input the same after removing the duplicates. However, I am unsure on how to incorporate an input array in this, and right now it has the elements hardcoded. This is my first week of programming so I apologize if this is a silly question. This is the code:
#include <stdio.h>
#include <stdbool.h>
#define nelems 8
int main()
{
int l[nelems] = {1,2,3,1,4,4,5,6};
for(int m=0;m<nelems;m++)
{
bool wase = 0;
for(int n=0;n<nelems && m>n;n++)
{
if (l[m] == l[n] && m != n)
wase = 1;
}
if (wase == 0){
printf("%d\n", l[m]);
}
}
return 0;
}
Try using a for loop and scanf.
int i;
for(i=0;i<nelems;i++){
scanf("%d",&l[i]);
}
This is what you need.
#include <stdio.h>
#include <stdbool.h>
#define nelems 8
int main()
{
int i;
int l[nelems] ;
for(i=0;i<nelems;i++)
{
printf("enter %d number :",i);
scanf("%d",&l[i]);
}
for(int m=0;m<nelems;m++)
{
bool wase = 0;
for(int n=0;n<nelems && m>n;n++)
{
if (l[m] == l[n] && m != n)
wase = 1;
}
if (wase == 0){
printf("%d\n", l[m]);
}
}
return 0;
}
If you like int-type array, you can just declare another one:
int input[nelems];
and follow the user968000 advice, remembering that when you are typing the sequence in your console you have to put a white space between each number.
To avoid that, I'd rather use char-type arrays, declared as follows:
char l[nelems] = {'1', '2', '3' /*etc.*/};
char input[nelems];
Then you make a for loop, as user968000 suggested:
int i;
for(i=0;i<nelems;i++)
scanf("%c", &input[i]);
In this case you won't need the white spaces between the digits. Notice the '&' character in the scanf function: just put it as I showed, you'll surely learn what it is in next lessons.
So you have an input array and you can handle it as you want.
I would appreciate some help with this. I'm trying to create this simple program that repeatedly loops asking for the user to enter in an int. If he enters an int, it exits but if he enters something else or bigger than int (ex.4gs4r33) it will loop again asking to enter an int. This is what I have tried, and it's not working. It says it's an int even if it's not.
#include<stdio.h>
unsigned int findInt();
int main() {
printf("Please input an int.\n");
findInt();
}
unsigned int findInt() {
char input;
long num = 0;
int b = 0;
do {
scanf("%c", &input);
if (isdigit(input)){
num = num*10+input+'0';
b = 1;
}
else if (input == '\n')
b = 1;
else
b = 0;
} while(input != '\n');
if (b == 1)
printf("Great!\n");
else{
printf("Not an int \n");
findInt();
}
return 0;
}
Two possible approaches. One would be to modify your code:
b = 1; // start off with good intentions…
do {
scanf("%c", &input);
if (isdigit(input)){
num = num*10+input -'0'; // *** SUBTRACT '0', don't add it!
}
else if (input != '\n') {
b = 0;
break; // *** break when you find non-digit
}
} while (input != '\n');
Two changes: getting the math right as you compute the integer, and fixing the logic (so you break out of your loop when you find a non digit character)
Second approach:
char buf[100];
char intAsString[100];
fgets(buf, 100, stdin);
sscanf(buf, "%d", num);
sprintf(intAsString, "%d\n", num);;
if(strcmp(buf, intAsString) == 0 ) {
printf("yay - you entered an integer!\n");
}
I'm sure you can figure out how that works.
update a complete code snippet that solves the issue of "loop logic" as well: you call the findInt function once from the top level, and it keeps going until you get the int. Note - in order for this to work properly, I read the entire input at once (rather than one at a time), then pick off the characters one by one using sscanf (and updating the pointer manually). It has a number of advantages - not least of which is that you start with a fresh input every time you call findInt, instead of having the rest of the input buffer that still needs reading (and which was giving rise to "no,no,no,great!" - as you would keep reading the bad input until you got to the newline, and accept that...)
#include<stdio.h>
#include <ctype.h>
unsigned int findInt();
int main() {
findInt();
}
unsigned int findInt() {
char input;
char buf[100];
char *temp;
long num = 0;
int b = 0;
printf("please enter an int:\n");
fgets(buf, 100, stdin);
temp = buf;
do {
sscanf(temp++, "%c", &input);
if (isdigit(input)){
num = num*10+input-'0';
b = 1;
}
else if (input == '\n')
{
b = 1;
break;
}
else {
b = 0;
break;
}
} while(input != '\n');
if (b == 1)
printf("Great! %d is an integer!\n", num);
else{
printf("Not an int \n");
findInt();
}
return 0;
}
In the else branch - i.e. not a digit or a newline - you set b to 0. Now if a digit DOES follow you reset that to 1.
You'll probably want to break or somehow record the permanent failure instead of just continuing.
#include <stdlib.h>
#include <limits.h>
#include <stdbool.h>
void findInt(){
int x;
bool ok;
do{
char buff[32], *endp;
long long num;
ok = true;//start true(OK)
printf("Enter a number: ");
fgets(buff, sizeof(buff), stdin);
//strtoll : C99
x=(int)(num=strtoll(buff, &endp, 0));//0: number literal of C. 10 : decimal number.
if(*endp != '\n'){
if(*endp == '\0'){
printf("Too large!\n");//buffer over
while('\n'!=getchar());
} else {
printf("Character that can't be interpreted as a number has been entered.\n");
printf("%s", buff);
printf("%*s^\n", (int)(endp - buff), "");
}
ok = false;
} else if(num > INT_MAX){
printf("Too large!\n");
ok = false;
} else if(num < INT_MIN){
printf("Too small!\n");
ok = false;
}
}while(!ok);
}
,
I wanted to make a C program that finds the numbers in the input array and then multiplies it all together, I made the program but it got an issue that I don't know, can anybody help me with it!?
Here is the code!
#include <stdio.h>
#include <stdlib.h>
int main ()
{
char t[10];
int n, z;
n = 0;
printf ("please enter a code: \n");
scanf ("%s", t);
while (n != '\0')
{
if (isdigit (t[n] == 0))
{
n++;
}
else
{
z = t[n];
z *= z;
}
}
printf ("%d", z);
}
Here is updated code. There is a comment for each bug that needed correction.
(Note that the comment describes the intention of the corrected code, it doesn't describe the bug.)
int temp;
z=1; // Initialize z
printf ("please enter a code: \n");
scanf ("%s", n);
while (t[n] != '\0') { // While there are more characters in the string
if (isdigit (t[n])) { // Check if the character is a digit
temp = t[n] - '0'; // Convert character digit to corresponding number.
z *= temp;
}
n++;
}
Your first problem is that you don't actually use t in your while loop. Your while loop only uses n which is set to 0 and never modified.
Your second problem is that you may be better off to use scanf("%d", &number); to scan numbers straight away.
z should be initialized to 1. and remove "z = t[n];"
#include <stdio.h>
#include <string.h>
main()
{
char a[5] ;
int b=1, n=0,m=0;
scanf("%s",a);
while (n <5 )
{
if (!isdigit(a[n]))
{
n++;
m++;
}
else{
b *= (a[n]-'0');
n++;
}
}
if(m==5) b=0;
printf("%d\n",b);
}