An extra blank line before the program terminates - c

I'm really new to programming and just wanted to ask a quick question.
So I made this program that reads off whatever the user inputs, then output the exact same thing until the user presses enter without any input.
int main(void) {
char s1[30];
while (s1[0] != NULL) {
gets(s1);
printf("%s\n", s1);
}
system("PAUSE");
return 0;
}
Then I realized that when I press enter to end the program, the program creates an extra blank line before the program terminates.
So I changed my code as it is below
int main(void) {
char s1[30];
while (1) {
gets(s1);
if (s1[0] == NULL)
break;
printf("%s\n", s1);
}
system("pause");
return 0;
}
And now the program terminates without creating an extra blank line. But I really can't seem to figure out the factors that made the difference between two codes.
Any help would be appreciated. Thanks!

As already told in the comment section don't use gets it is dangerous(why-is-the-gets-function-so-dangerous-that-it-should-not-be-used).
And replace gets with fgets as below.
while (fgets(s1,sizeof s1,stdin)) {
if (s1[0] == '\n') //fgets() reads the newline into the buffer
break;
printf("%s", s1); // Don't need to append \n to print as s1 will be having \n already.
}
To answer your question
gets(s1);
if (s1[0] == NULL) // Not valid comparison use \0 instead of NULL
When you press enter to terminate the program, gets will not read the newline(\n) character into the buffer hence your s1 will be untouched by gets and will have indeterminate values(seemingly it is having 0's in your case) so you are hitting if (s1[0] == NULL) and breaking out of the loop without printing newline.

Related

Program is not accepting second string and giving output directly

Here I want to compare two strings in case2. case 1 works well but when I go to case 2 it's not asking for second string input and directly prints "Both strings are different"[1]
[1]: https://i.stack.imgur.com/l2J6L.jpg
#include <stdio.h>
#include <stdlib.h>
#define size 20
int main ()
{
char str1[size],str2[size];
int operation,error=0,i=0;
printf("Enter String: ");
fgets(str1, size, stdin);
do {
printf("1.Copy\n2.Compare\n3.Exit\nWhich operation you want to do:");
scanf("%d",&operation);
switch (operation) {
case 1:
for (int i=0; str1[i] != '\0'; i++) {
str2[i] = str1[i];
}
printf("First string: %s\n",str1);
printf("Second string: %s\n",str2);
break;
default:
printf("Error");
break;
case 2:
printf("Enter second string: "); // it's not executing (Not takin input) and directly i get o/p of line 39
fgets(str2, size, stdin);
for (i=0; str2[i] != '\0'; i++) {
if (str1[i] != str2[i]) {
error++;
}
}
if (error == 0) {
printf("Both strings are same.\n");
}
else
printf("Both strings are not same.\n");
break;
}
} while (operation != 3);
}
As scanf leaves behind a dangling newline character \n it causes the fgets to not wait for the input from the user. Try flushing the input buffer by using getchar.
Update: Added loop to remove all the characters which are skipped by the scanf but can be entered by the user like extra white spaces after the number.
...
do {
printf("1.Copy\n2.Compare\n3.Exit\nWhich operation you want to do:");
scanf("%d",&operation);
int ch;
while ((ch = getchar()) != '\n' && ch != EOF);
switch (operation) {
...
Reference: faq.cprogramming.com
Since your strings are lines, scanf() is not a good choice except for getting the integer value, and to clean the buffer of everything after that (might be all sorts of junk, never trust a user), do a fgets into str2. Your new lines will compare, too, if they are identical. You should also test the return from scanf is 1, saying you got a number! What if a user types in 'x' as the number? If you want to ask again, you need to clean the junk out of the buffer. Remember that, since you have 'cooked' input, nothing is sent until the user hits enter, so you always need to deal with the new line character. If all you do is scanf in numbers, scanf will got through an new line as white space seeking a digit, but you are doing mixed string and number input.
You need to compare a null to mis-compare if one string is a prefix of the other, so in 'for' test 'i < size' but break out of the loop if both strings have a null at the same point ( !str1[i] && !str2[i] ) or on the first miscompare (setting error). There is no point in comparing past the first miss! In the prefix case, the null mis-compares some other char value.
Since trailing spaces are part of your string, you might print them in single quotes (after removing the new line).

stopping scanf on pressing enter

I am writing a C program which takes string input and print each word in a separate line. But the program is not stopping even after pressing enter. Please suggest a solution.
#include<stdio.h>
#include<string.h>
int main(void)
{
char str[50];
while(scanf("%s",str)&&strcmp(str,"\n"))
printf("%s\n",str);
}
You need to use fgets to read the line and if the input is just a single character which is newline character then break else keep continuing.
while(fgets(str,sizeof(str),stdin))
{
if(strcmp(str,"\n") == 0)
break;
else
{
size_t n = strlen(str);
if(n>0 && str[n-1] == '\n')
str[n-1] = '\0';
printf("%s\n",str);
}
}
PS: fgets() comes with a newline character and we need to supress the newline character as shown above.

Printf printing everything in function before completing commands?

I have a piece of code here:
Tree *rangeprint(Tree *t) {
char first[20];
char last[20];
int f = 0;
int l = 0;
printf("First Entry?\n");
while(1) {
first[f] = getchar();
if(first[f] == '\n') {
first[f] = '\0';
break;
}
f++;
}
printf("Last Entry?\n");
while(1) {
last[l] = getchar();
if(last[l] == '\n') {
last[l] = '\0';
break;
}
l++;
}
printf("%s %s\n", first, last);
}
When I run this code, the output I get in the console is:
First Entry?
Last Entry?
Why is it skipping over the while loops and printing everything before executing them?
UPDATE - I changed the termination condition to 'x' instead of '\n' and sure enough it prints properly.
Adding a random getchar() before the loop starts fixes the problem, since the '\n' is read into there.
It is printing them, it's just that they are empty strings! (hint: f and l doesn't change - I assume the last loop using f is a typo!)
The getchar reads from the std in. If there is any newline character in previous input, It can cause the issue.
Just put,
fflush(stdin);
after
printf("First Entry?");
You are not advancing the pointer f while reading characters from the input. You are overwriting chatacter at location 0 all the times and in the end location 0 contains \0
try to put an \n at the end
printf("First Entry?\n");
printf("Last Entry?\n");

C - Return the first non-whitespace character

I have been asked to write a function that returns the first non-whitespace character in an inputted string.
It's working when I enter something like "hello" or anything that does not begin with a white space. But when I enter something like " hello", it returns a white space.
Here is my code:
int question6()
{
printf("Start typing stuff in \n");
char myChar = returnFirstNonWhite();
printf("First non-white space character is: %c",myChar);
}
int returnFirstNonWhite()
{
int ch,temp;
ch = getchar();
while (ch != 32)
{
temp = ch;
printf("Found first success %c\n", ch);
}
return temp;
}
ch = getchar();
while (ch == 32)
{
ch = getchar();
}
return ch;
One easy option would be to use scanf() instead of getchar(). scanf() will take a string (so there's no need to loop getting chars) and it will strip off any starting white space, so you just need to grab the first character it has.
int returnFirstNonWhite()
{
char str[50];
memset(str, '\0', 50);
scanf("%s", str);
return str[0];
}
so
>> hello
will return 104 (ascii 'h')
At first you are taking only one character input. And if it is not equal to 32 int value, the program should be in a infinite loop!!!! This is a nothing code.
Everything here appears to be okay, except in your while loop you don't continue to fetch the next character. In other words, it fetches the initial character, let's say a whitespace, and then continues in that while loop forever since the ch variable is never changed.
Try adding ch = getchar(); within your while loop so it continually fetches the next character to check. Also, I just realized you need to check that the character is equal to 32, not not equal so that if the character is a whitespace it continues to fetch the next character.

c Exit if string is empty

I have the below code which is supposed to exit if the provided user input is empty i.e they press [ENTER] when asked for the input. However it doesnt do anything if [ENTER] is pressed.
printf("Enter the website URL:\n");
scanf("%s", str);
if(strlen(str) == 0) {
printf("Empty URL");
exit(2);
}
If the user just presses enter, the input will still contain a newline ('\n'). Your condition should be
if (!strcmp(str, "\n"))
I use a isempty function:
int isempty(const char *str)
{
for (; *str != '\0'; str++)
{
if (!isspace(*str))
{
return 0;
}
}
return 1;
}
Also, I would recommend using fgets over scanf, as scanf is unsafe and can lead to buffer overflows.
fgets(str, /* allocated size of str */, stdin);
%s with scanf() will discard any leading whitespace, of which it considers your Enter keypress. If you want to be able to accept an "empty" string, you'll need to accept your input in another way, perhaps using fgets():
printf("Enter the website URL:\n");
fgets(str, SIZE_OF_STR, stdin);
if(!strcmp(str,"\n")) {
printf("Empty URL");
exit(2);
}
Keep in mind the above code does not consider EOF, which would leave str unchanged.
shouldn't you check for '\n' - new line? Enter will represented as a new line character '\n'

Resources