You are here:

C/converting from integer to ascii??

Advertisement


Question
QUESTION: Hi,

is there a simple way to convert an integer to ascii?? I'm supposed to try implement my own version of the itoa function. Would you be able to reverse the ascii to integer function?

thanks

ANSWER: Hello Mark

Implementing itoa is not difficult. I will describe to you the basic idea. You try to implement it. If you have problems, show me how far you got and I'll help you more.

Basically you have to pick off each individual digit, change it to a character, and store the character into an array. Isolating each digit is easy with the modulo operator (%). Take your integer, mod it by 10, and the result will be the last digit.

For example if you have
number = 123;
digit = number % 10 will make digit have 3
Then you have to divide number by 10 so that it becomes 12. We're doing integer division here so the factional parts are chopped off.

For every digit you isolate with the mod operator, you need to add the ASCII character code for the zero character. You do it like this:
char character = digit + '0'; /* that is a zero in single quotes */

Then you have to put the character into the array.

You keep doing the above steps until number is 0. When number is 0 the conversion is done.
Finally, when your loop is done, don't forget to add a zero byte to your array so that it is a proper C string.

Now print out your array. You will notice that the numbers come out in reverse order. This is because the array was built in reverse order. The algorithm places the last digits of number into the array first.

You will need to make another function to reverse the array. I'm willing to guide you with that too but first show me your attempt.

Once all that is done you will notice that the program will not work for negative numbers. Fixing the program to work for negative numbers is very simple so don't worry about it right now.


Best regards
Zlatko


---------- FOLLOW-UP ----------

QUESTION: Hi Zlatko,

here is my attempt, I hope I did it correctly. I have integer of 123, I get 51 as output...


Also, I commented out a function prototype, when I try sticking the stuff in the main into a separate function, the Visual C++ 2008 express compiler give errors. Another thing, how to know length of integer for the purposes of knowing what the limits of the for loop is (if that is important at all)?

thanks,
Mark

#include<stdio.h>

//void intToAscii(void);

int main(void)
{
  char array[20], character;
  int digit, counter, number, i;

  number = 123;
  counter = 0;
  
  for(i = 0; i < 20; i++)
  {
     digit = number % 10;
     character = digit + '0';
     array[counter] = character;

     if(digit == 0)
        break;
  }

//   counter++;
//   array[counter] = '\0';   

  printf("%d", array[counter]);

  
  return 0;
}

ANSWER: Hello Mark.
That is a good attempt.

I would say that you don't need a "for" loop. You need a while(number != 0) loop. With each iteration of the loop, the number will be divided by 10. Eventually number will become 0 and the loop will end. Don't forget to add the division by 10 into the program.

You also need to increment your array counter after the character is placed into the array.

Do not break out of the loop just because digit is 0. You can have a number like 100 with zero digits. A zero digit does not mean the conversion is done.

The line
array[counter] = 0
should be placed back into the program.

The printf should look like this:

printf("%s", array);
the array is a C character string so use "%s" to format it.

---------- FOLLOW-UP ----------

QUESTION: Hi Zlatko,

I got the program to work the way you suggested, and also I wrote the part to reverse the order in which the output is printed out to the screen. I'm wondering how to get the program split up into smaller functions to be more readable and easier for future editing, but I'm getting errors when I do that way.


#include<stdio.h>

int main(void)
{
  char array[20], character;
  int digit, counter, number;

  counter = 0;

  printf("Input a number: ");
  scanf("%d", &number);

// converting integer to ascii
  while(number != 0)
  {
     digit = number % 10;
     number /= 10;
     character = digit + '0';
     array[counter] = character;
     counter++;
  }
  
  array[counter] = '\0';   
  printf("%s\n", array);
  
  printf("%d\n\n", counter);

  //correcting output
  int i, j;
  char t;

  for(i=0; array[i]!='\0'; i++)
     i--;

  for(j=0; j<=i/2; j++)
  {
     t = array[j];
     array[j] = array[j-i];
     array[j-i] = t;
  }

  return 0;
}

Answer
Hello Mike

That's great. You just about have it done. I've put it into functions for you so that you can see how it is done.

The program works for positive numbers and now works for a 0 input as well. Now you need to handle negative numbers. The problem with negatives is that the modulo operator on a negative returns a negative. There are a couple of ways of handling it. Give me some ideas.

The rest of my answer is in comments in the code.

#include<stdio.h>
#include<string.h>

/*
forward function declarations
With these you can put your functions below the callers
Meaning you can put the functions below main
*/
char* myItoA(int number);
void reverseString(char* input);



void reverseString(char* input)
{
   int i, j;
   char t;

   /*  You should use strlen to calculate the length.
       The lines below don't work because the for loop increments i
       but the loop body decrements i. It ends up an infinite loop
       doing nothing.

   for(i=0; input[i]!='\0'; i++) <---- i incremented here
       i--; <---- this is the loop body. i is decremented here

       The correct way to write the above is
       for(i=0; input[i]!='\0'; i++) ; <-- semicolon means empty loop
       i--;

   */
   i = strlen(input)-1; // <--- use this instead
   i = i / 2; /* You can do your division here so that it
         does not have to be recalculated every time through the loop
   */
   for(j=0; j<=i; j++)
   {
       t = input[j];
       input[j] = input[i-j]; //<--- you want i-j, not j-i. j starts at 0, j-i would give a negative
       input[i-j] = t;
   }
}

/*
You have three choices about how to get the result from myItoA back to the caller.
1)You can have the caller pass in the required space.
Advantage: the function is thread safe. That is probably not important to you now.
Disadvantage: the caller may pass in an array too small to hold the result.

2)You can have the program allocate memory and pass it back to the caller
Advantage: the function is thread safe.
Disadvantage: the caller must remember to free the result or memory is wasted

3)You can declare a static array inside of the function and return it
Advantage: The function can guarantee that the array is large enough to hold the result
The function is easy for the caller to use.
Disadvantage: The function is not thread safe.

Thread safety is not important to you right now and even a professional function can be written
this way as long as it is clearly documented that it is not thread safe so I suggest you use
method 3.

*/
char* myItoA(int number)
{
   /*
   The static keyword in the array declaration means that the memory of the array will remain
   valid after the function returns. If the array was not declared static, the memory taken up
   by the array would become invalid after the function returned and may be reused for other things
   by the time you get around to printing its contents.
   */

   static char array[20];
   int digit;
   char character;
   int counter = 0;

   // converting integer to ascii
   /*
   Notice that the original while loop would not work if the input number was 0.
   The loop needs to execute once even when the number is 0. When a loop needs
   to execute at least once, we use a do while so that the loop exit condition is
   checked after the loop runs.
   */
   do
   {
       digit = number % 10;
       number /= 10;
       character = digit + '0';
       array[counter] = character;
       counter++;
   } while(number != 0);

   array[counter] = '\0';

   reverseString(array);

   return array;

}

int main(void)
{
   int number;

   while(1) // testing loop
   {
       printf("Input a number: ");
       scanf("%d", &number);
       printf("result is '%s'\n", myItoA(number));
   }


   return 0;
}

C

All Answers


Answers by Expert:


Ask Experts

Volunteer


Zlatko

Expertise

No longer taking questions.

Experience

No longer taking questions.

Education/Credentials
No longer taking questions.

©2012 About.com, a part of The New York Times Company. All rights reserved.