0

I am trying to write a simple c program that takes input using scanf, and ensures that this input is an integer. To do this I have written a recursive function, but the function goes into an infinite loop if I enter a non-integer character. I've attatched the code below.

#include <stdio.h>

int getInput() {
  int success = 0;
  int input;

  printf("Enter a positive integer: \n");
  success = scanf(" %d", &input);

  if (success == 0 || input < 0) {
    return getInput();
  }else return input;
}
Vlad from Moscow
  • 301,070
  • 26
  • 186
  • 335
  • 3
    You have to remove the stuff that`scanf()` can't process as an integer before trying again — but you don't, so it fails again, and recurses again, and ends up crashing. Probably add: `if (success != 1) { int c; while ((c = getchar()) != EOF && c != '\n') ; }` inside your `if` statement. – Jonathan Leffler Feb 03 '22 at 19:48
  • 4
    `scanf` is arguably not a good tool for parsing uncontrolled input. This is one example of it. An alternative is `fgets` followed by `sscanf`. – kaylum Feb 03 '22 at 19:49
  • 1
    another option would be getline() + strtol() (or sscanf istead of strtol, idk), although management of memory with getline is not super easy, you can learn a thing or two – wojand Feb 03 '22 at 19:52
  • Are you testing your code on non-integer input because someone told you it's a case you have to handle, or because you thought it was a good idea? If the latter, my advice to you is: *just don't worry about it*. If you're using `scanf`, it turns out that worrying about unexpected input is not a good idea, after all, because properly handling it is next to impossible. (If you want to properly handle bad input, the first thing to do is to [not use `scanf`](https://stackoverflow.com/questions/58403537). – Steve Summit Feb 03 '22 at 20:43
  • 1
    In general, though, recursion is not a good way to "go around again" after rejecting bad input. Better to just use an ordinary loop. – Steve Summit Feb 03 '22 at 20:46

1 Answers1

2

The problem is that if a non-number is entered the input buffer contains a garbage. You need to clear the input buffer before trying to enter another number.

Using your approach with the call of scanf the function can look for example the following way

int getInput( void ) 
{
    int input = 0;

    printf("Enter a positive integer: \n");
  
    if ( scanf( "%d", &input) != 1 )
    {
        scanf( "%*[^\n]" ); 
    }

    return input <= 0 ? getInput() : input;
}

Another more complex approach is to use the function fgets and strtol and check their results.

Vlad from Moscow
  • 301,070
  • 26
  • 186
  • 335