Question

I'm trying to solve the problem here but I don't know why my code isn't working. Any help is appreciated. EDIT: Edited to make correction mentioned below, but there is still an extra "15" (in bold) on the second line of the output and I don't understand where it is coming from.

My output is

18662658515 555227215

#include <stdlib.h>
#include <stdio.h>

int main(void){
  int n;
  int j;
  scanf("%d\n", &n);
  int i = 0;
  char mystr[15];

  for(;i<n;i++){
    fgets(mystr,15,stdin);

    for(j=0;j<15;j++){
      if(isdigit(mystr[j])){
        printf("%c", mystr[j]);
        continue;
      }
      if ('A' <= mystr[j] && mystr[j] <= 'C')
        printf("2");
      if ('D' <= mystr[j] && mystr[j] <= 'F')
        printf("3");
      if ('G' <= mystr[j] && mystr[j] <= 'I')
        printf("4");
      if ('J' <= mystr[j] && mystr[j] <= 'L')
        printf("5");
      if ('M' <= mystr[j] && mystr[j] <= 'O')
        printf("6");
      if ('P' <= mystr[j] && mystr[j] <= 'S')
        printf("7");
      if ('T' <= mystr[j] && mystr[j] <= 'V')
        printf("8");
      if ('W' <= mystr[j] && mystr[j] <= 'Z')
        printf("9");
    }
    printf("\n");
  }
}
Was it helpful?

Solution

The problem is that you're iterating over all 15 characters in the input string, regardless of the length of the input. The first test case has 11 characters, but the second case has only 8. In the second iteration, you're accidentally processing the last two characters from the first input, which were 15.

To fix it, just stop your iteration when you hit the NUL character 0, which terminates the string by changing this line

for(j=0;j<15;j++){

to

for(j=0; mystr[j] != 0; j++){

OTHER TIPS

For one thing, I think your comparisons are backwards. For example, you should be testing "if ('A' <= mystr[j] && mystr[j] <= 'C')".

It would be helpful, perhaps, to have a function between() (with apologies; my C is rusty):

bool between(char c, char before, char after) {
    return before <= c && c <= after;
}

so

if ('A' <= mystr[j] && mystr[j] <= 'C')
        printf("2");

becomes

if (between(mystr[j], 'A', 'C')
        printf("2");

It is generally better to use half-open ranges, where the lower limit is inclusive and the upper limit exclusive. With this, then, the last element of each test would be the first element of the preceding test, which could help you detect certain kinds of bugs more readily.

consider that you might want to compare things in the same order. Speak this out in plain english before writing code. If myLetterCode is Greater Than A.code && myLetterCode is Less than C.Code (it must be B!).

keep your letter on the left and the thing you're comparing it to on the right. Otherwise it gets very confusing very fast.

Wouldn't this be easier with a lookup table?

int numbers[] = {              2, 2, 2,  3, 3, 3,
                     4, 4, 4,  5, 5, 5,  6, 6, 6,
                  7, 7, 7, 7,  8, 8, 8,  9, 9, 9, 9};

... cut ...

if (isdigit (mystr[j]))
    printf ("%c", mystr[j]);
else
    printf ("%d", numbers[mystr[j] - 'A']);

... cut ...
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top