hec hec - 4 months ago 25
C Question

why does this program crash when input is greater than 9?

I dont know why this crashes on my machine but it does

You are given a positive integer, N ,:

If 1 <= N <= 9, then print the English representation of it. That is "one" for 1, "two" for 2, and so on.
Otherwise print "Greater than 9" (without quotes).
Input Format:

Input will contain only one integer, N .

#include <stdio.h>

const char* itos2(int);

int main() {
/* Enter your code here. Read input from STDIN. Print output to STDOUT */
int a;
scanf("%i", &a );
printf("%s",((a >= 1 || a <= 9) ? itos2(a) : "Greater than 9"));

//printf("%s",itos2(a)); this doesn't crash provided a default label is set
return 0;
}

const char* itos2(int a)
{
const char* str [] = { "one" , "two", "three", "four", "five", "six", "seven", "eight", "nine"};
switch(a)
{
case 1 : return str[0];
case 2 : return str[1];
case 3 : return str[2];
case 4 : return str[3];
case 5 : return str[4];
case 6 : return str[5];
case 7 : return str[6];
case 8 : return str[7];
case 9 : return str[8];
default: return "Greater than 9";
}
}

Answer

Here's your code, improved:

#include <stdio.h>

const char* itos2(int);

// A proper C function prototype
int main(void)
{ 
   int a;

   // Checking the return value of scanf is *required*!
   // If it doesn't return a value which is equal to the number of expected
   // assignments, then your variables are left unassigned, leading to 
   // Undefined Behavior!
   if (scanf("%i", &a) != 1) {
       fprintf(stderr, "Invalid input\n");
       return 1;
   }

   // It's usually better practice to not have to worry about a valid range
   // of inputs when calling a function. Let this function worry about the
   // input checking.
   printf("%s", itos2(a));

   return 0;
}

const char* itos2(int a)
{
    const char* str [] = {
        "zero",
        "one",
        "two",
        "three",
        "four",
        "five",
        "six",
        "seven",
        "eight",
        "nine",
    };

    // Check boundary conditions. Checking just one boundary case and 
    // returning is simpler and less error-prone than your previous code.
    if (a < 0)
        return "Less than zero";
    if (a > 9)
        return "Greater than nine";

    // Why bother with a switch/case statement when you can simply
    // use the input value to index directly into an array of the strings?
    return str[a];
}

Assuming you're using GCC, always compile with at least this set of options:

gcc -Wall -Werror ...