1

I want to break this loop when the user press enters twice. Meaning, if the user does not enter a character the second time, but only presses enter again, the loop must break.

char ch;
while(1) {
    scanf("%c",&ch);
    
    if(ch=='') { // I don't know what needs to be in this condition
        break;
    }
}
Yun
  • 3,056
  • 6
  • 9
  • 28
  • 1
    Use [`fgets`](https://en.cppreference.com/w/c/io/fgets) to read full lines. If `fgets` return a non-null pointer, check if the length of the string is empty. That indicates an empty line. – Some programmer dude Aug 30 '21 at 10:52
  • Also please take some time to read [the help pages](http://stackoverflow.com/help), take the SO [tour], read [ask], as well as [this question checklist](https://codeblog.jonskeet.uk/2012/11/24/stack-overflow-question-checklist/). Lastly if you want to ask a C question, then please don't add other irrelevant language tags. – Some programmer dude Aug 30 '21 at 10:54
  • @Some But let me add that the question is in the upper 5 percent of first timer questions! It has some code (OK, doesn't compile as-is, but still) and a reasonable description of the intent and the problem. Upvoted :-). – Peter - Reinstate Monica Aug 30 '21 at 11:01
  • It is worth mentioning that `scanf`'s `%c` conversion is special in that it does not ignore newline but simply scans it, like any other byte in the input stream. Most other conversions like %d, %f, %s parse "words" and don't care about the whitespace, possibly including newline, that separates them. Questions like this one are typical for interactive exercise programs but rather untypical for real world problems: When is the last time you interacted with a console program in line mode? – Peter - Reinstate Monica Aug 30 '21 at 13:29

3 Answers3

2

It is not possible to detect keypresses directly in C, as the standard I/O functions are meant for use in a terminal, instead of responding to the keyboard directly. Instead, you may use a library such as ncurses.

However, sticking to plain C, we can detect newline characters. If we keep track of the last two read characters, we can achieve similar behavior which may be good enough for your use-case:

#include <stdio.h>

int main(void)
{
    int currentChar;
    int previousChar = '\0';
    while ((currentChar = getchar()) != EOF)
    {
        if (previousChar == '\n' && currentChar == '\n')
        { 
            printf("Two newlines. Exit.\n");
            break;
        }
        if (currentChar != '\n')
            printf("Current char: %c\n", currentChar);

        previousChar = currentChar;
    }
}

Edit: It appears that the goal is not so much to detect two enters, but to have the user:

  • enter a value followed by a return, or
  • enter return without entering a value, after which the program should exit.

A more general solution, which can also e.g. read integers, can be constructed as follows:

#include <stdio.h>

#define BUFFER_SIZE 64U

int main(void)
{
    char lineBuffer[BUFFER_SIZE];
    while (fgets(lineBuffer, BUFFER_SIZE, stdin) != NULL)
    {
        if (lineBuffer[0] == '\n')
        {
            printf("Exit.\n");
            break;
        }

        int n;
        if (sscanf(lineBuffer, "%d", &n) == 1)
            printf("Read integer: %d\n", n);
        else
            printf("Did not read an integer\n");

    }
}

Note that there is now a maximum line length. This is OK for reading a single integer, but may not work for parsing longer input.

Credits: chux - Reinstate Monica for suggesting the use of int types and checking for EOF in the first code snippet.

Yun
  • 3,056
  • 6
  • 9
  • 28
1

You can store the previous character and compare it with the current character and enter, like this:

char ch = 'a', prevch = '\n';
while(1){
    scanf("%c",&ch);
    if((ch=='\n') && (ch == prevch)){// don't know what needs to be in this condition
        break;
    }
    prevch = c;
}

Note that the previous character by default is enter, because we want the program to stop if the user hits enter at the very start as well.

Lajos Arpad
  • 64,414
  • 37
  • 100
  • 175
0

Working like charm now

char ch[10];
while(1){
    
     fgets(ch, sizeof ch, stdin);
    
    if(ch[0]=='\n'){
        break;
    }
   
    
    
}
  • Never *ever* use `gets`! It's [so dangerous](https://stackoverflow.com/questions/1694036/why-is-the-gets-function-so-dangerous-that-it-should-not-be-used) so it have even been removed from the C standard. Better use `while (fgets(ch, sizeof ch, stdin) != NULL && strlen(ch) != 0) { /* Main part of the loop */ }` – Some programmer dude Aug 30 '21 at 11:12
  • 1
    This does not detect "until double enter". It only detects an empty line. If the first line was empty, the loop breaks. If _line_ was `"123456789\n"`, this code would exit the loop. IAC, better code would also check the return value of `fgets()`. – chux - Reinstate Monica Aug 30 '21 at 12:18
  • @chux-ReinstateMonica Why would the program exit the loop when encountering `"123456789\n"`? – Peter - Reinstate Monica Aug 30 '21 at 13:34
  • 1
    In order to receive an upvote from me a post should typically, in addition to providing a solution to the question: (1) *Explain* the solution, ideally mentioning any stumbling blocks, and give a rationale why it is better than possible other solutions; (2) perform error checking (or, possibly, an explicit remark that it is missing in order to not distract from the subject matter being discussed); (3) format the code properly; (4) ideally, use language that is reasonably respectful and correct. – Peter - Reinstate Monica Aug 30 '21 at 13:44
  • @Peter-ReinstateMonica "Why would the program exit the loop when encountering "123456789\n"" --> First `fgets(ch, 10, stdin)` reads in `"123456789"`, next `fgets(ch, 10, stdin)` reads in `"\n"`. Loop exits. – chux - Reinstate Monica Aug 30 '21 at 15:06
  • @chux-ReinstateMonica Oh, it's the buffer size, right. – Peter - Reinstate Monica Aug 30 '21 at 15:12