Decimal To Binary conversion using Array and Stack - c

This is the C Program I have written to convert a Decimal number to it's equivalent Binary number. I have used Stack (implemented using array) and the following algorithm:
Number is divided and remainders are pushed in stack.
Remainders are popped one at a time and converted into Binary
The Problem is that the program works fine for numbers up to 3, after that from 4 on wards, each Binary Number comes one less than the actual number.
// Decimal to Binary conversion using Stack
#include<stdio.h>
#include<math.h>
#define max 20
int top=-1, stk[max];
void push(int);
int pop(void);
int main()
{
int i,num,x,flag=0,s, bin=0, factor;
printf("Enter any decimal number: ");
scanf("%d",&num);
while(num>0)
{
if(num==1)
push(num);
else
{
x = num%2;
push(x);
}
num/=2;
flag++;
}
for(i=0;i<flag;i++)
{
s = pop();
bin = bin + s*pow(10,(flag-1-i));
}
printf("\nEquivalent Binary number is --> %d",bin);
return 0;
}
void push(int n)
{
if(top == max-1)
{
printf("Error! Overflow");
return;
}
stk[++top] = n;
}
int pop(void)
{
int y;
if(top == -1)
{
printf("Error! Underflow");
return;
}
y = stk[top];
top = top-1;
return y;
}
Will anybody help me by finding the logical flaw?
Thank You

My answer is your program is unnecessarily complicated.
#include<stdio.h>
int main()
{
unsigned num, i, zeros = 0;
printf("Enter a decimal number: ");
scanf("%u", &num);
printf ("Decimal %u in binary is ", num);
for (i=sizeof(unsigned)*8; i>0; i--)
{
if ((int)num < 0) // get MSB
zeros = printf ("1"); // cancel 0-suppresion
else if (zeros)
printf ("0");
num <<= 1;
}
printf ("\n");
return 0;
}

The function pow return a double that can have a 9999999... after the decimal point, which is rounded to the floor when it is casted to int, you can fix your problem using ceil() function, that returns the smallest integer value greater than or equal the argument, like this.
bin = bin + ceil(s*pow(10,(flag-1-i)));

//C Program to convert Decimal to binary using Stack
#include<stdio.h>
#define max 100
int stack[max],top=-1,i,x;
/*------ Function Prototype------------*/
void push (int x)
{
++top;
stack [top] = x;
}
int pop ()
{
return stack[top];
}
/*-------------------------------------*/
void main()
{
int num, total = 0,item;
printf( "Please enter a decimal: ");
scanf("%d",&num);
while(num > 0)
{
total = num % 2;
push(total);
num /= 2;
}
for(i=top;top>-1;top--)
{
item = pop ();
printf("%d",item);
}
}

Here is a simpler version of your above program
int main(){
int n,remainder;
printf("Enter a decimal number:");
scanf("%d",&n);
while(n!=0){
remainder = n%2;
n = n/2;
push(remainder); // inserting in stack
}
display(); // displaying the stack elements
}
reference of above code
C program to Convert Decimal number into Binary using Stack

So I've done the math on several numbers, and this appears to be correct. I would agree with others that this is needlessly complicated, but that is not causing your issues on it's own, it's just making them harder to find.
So the output of this program appears correct, from a logical standpoint. Lets look into other potential issues:
You're indexing an array with an int that you initialize to -1
This is bad practice, and unnecessary. Array indexes in C can never be negative, so the compiler will assume this is an unsigned number, so if you have a 32 bit processor, it will assume you're trying to get array[2^32 - 1], which is not what you want. Always use a unsigned value for array indexes
What MIGHT be happening, and I'm not certain, is that your compiler is doing something with this behind the scenes which is screwing up your program, it's really hard to say. But it's probably attempting to convert your negative number into an unsigned int before you do your addition. Fix this by changing your declaration of top to:
unsigned int top = 0;
and changing where you access top from:
stk[++top] = n;
to
stk[top++] = n;
You will also have to change
y = stk[top];
top = top-1;
to
top = top-1;
y = stk[top];
I'd say start there. I'd also suggest removing the pow line, and just individually printing each piece of the array, because it will output in the same way, and you already have all the info there ie.
PRINTF("%d%d%d",stk[2],stk[1],stk[0]);

Related

C code to find number of digits in integer is not working as per.suggest modifications

here is the link to the file(google docs link) containing my code -
#include<stdio.h>
int len(int);
void main()
{
int n,p;
printf("enter number");
scanf("%d",&n);
p=len(n);
printf("length of entered number is %d",p);
}
int len(int num)
{
int i,c,b;
for(i=1;i<=50;i++){
b=10*i;
if(num<b) {
return(i);
break;
}
}
}
Computing b=10*i; makes no logical sense. Did you want to raise 10 to a given power?
The normal way of solving this problem is to repeatedly divide by 10 until 0 is reached (using integer arithmetic), and count the number of divisions made. That is the number of digits in the original number. This method is also not vulnerable to integer overflow:
unsigned digits = 0;
for (; num /= 10; ++digits);
return digits;
int len(int num){
int i = 0;
if(num == 0)
return 1;
while(num!=0){
num = num / 10;
i++;
}
return i;
}
here we divide num by 10 until it reaches 0, and each time loop executes we increment the count i++
frontmatter i am not able to recognize your answer but i think this following code is helpful as per your title.
#include<stdio.h>
#include<conio.h>
void main()
{
char a[50000];
int i,c=0;
printf("enter number:");
fflush(stdin);
gets(a);
for(i=0;a[i]!='\0';i++)
{
if(a[i]>=0 || a[i]<=9)
{
c++;
}
}
printf("\n %d digit number",c);
getch();
}

How do I go through a certain number and extract digits smaller than 5 using a recursive function?

it's me again. I deleted my previous question because it was very poorly asked and I didn't even include any code (i'm new at this site, and new at C). So I need to write a program that prints out the digits smaller than 5 out of a given number, and the number of the digits.
For example: 5427891 should be 421 - 3
The assignment also states that i need to print the numbers smaller than 5 in a recursive function, using void.
This is what I've written so far
#include<stdio.h>
void countNum(int n){
//no idea how to start here
}
int main()
{
int num, count = 0;
scanf("%d", &num);
while(num != 0){
num /= 10;
++count;
}
printf(" - %d\n", count);
}
I've written the main function that counts the number of digits, the idea is that i'll assign (not sure i'm using the right word here) the num integer to CountNum to count the number of digits in the result. However, this is where I got stuck. I don't know how to extract and print the digits <5 in my void function. Any tips?
Edit:
I've tried a different method (without using void and starting all over again), but now i get the digits I need, except in reverse. For example, instead of printing out 1324 i get 4231.
Here is the code
#include <stdio.h>
int rec(int num){
if (num==0) {
return 0;
}
int dg=0;
if(num%10<5){
printf("%d", num%10);
dg++;
}
return rec(num/10);
}
int main(){
int n;
scanf("%d", &n);
int i,a;
for(i=0;i<n;i++)
{
scanf("%d", &a);
rec(a);
printf(" \n");
}
return 0;
}
Why is this happening and how should I fix it?
There is nothing in your question that specifies the digits being input are part of an actual int. Rather, its just a sequence of chars that happen to (hopefully) be somewhere in { 0..9 } and in so being, represent some non-bounded number.
That said, you can send as many digit-chars as you like to the following, be it one or a million, makes no difference. As soon as a non-digit or EOF from stdin is encountered, the algorithm will unwind and accumulate the total you seek.
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
int countDigitsLessThanFive()
{
int c = fgetc(stdin);
if (c == EOF || !isdigit((unsigned char)c))
return 0;
if (c < '5')
{
fputc(c, stdout);
return 1 + countDigitsLessThanFive();
}
return countDigitsLessThanFive();
}
int main()
{
printf(" - %d\n", countDigitsLessThanFive());
return EXIT_SUCCESS;
}
Sample Input/Output
1239872462934800192830823978492387428012983
1232423400123023423420123 - 25
12398724629348001928308239784923874280129831239872462934800192830823978492387428012983
12324234001230234234201231232423400123023423420123 - 50
I somewhat suspect this is not what you're looking for, but I'll leave it here long enough to have you take a peek before dropping it. This algorithm is fairly pointless for a useful demonstration of recursion, to be honest, but at least demonstrates recursion none-the-less.
Modified to print values from most significant to least.
Use the remainder operator %.
"The result of the / operator is the quotient from the division of the first operand by the second; the result of the % operator is the remainder. In both operations, if the value of the second operand is zero, the behavior is undefined" C11dr §6.5.5
On each recursion, find the least significant digit and test it. then divide the number by 10 and recurse if needed. Print this value, if any, after the recursive call.
static int PrintSmallDigit_r(int num) {
int count = 0;
int digit = abs(num % 10);
num /= 10;
if (num) {
count = PrintSmallDigit_r(num);
}
if (digit < 5) {
count++;
putc(digit + '0', stdout);
}
return count;
}
void PrintSmallDigits(int num) {
printf(" - %d\n", PrintSmallDigit_r(num));
}
int main(void) {
PrintSmallDigits(5427891);
PrintSmallDigits(-5427891);
PrintSmallDigits(0);
return 0;
}
Output
421 - 3
421 - 3
0 - 1
Notes:
This approach works for 0 and negative numbers.
First of all, what you wrote is not a recursion. The idea is that the function will call itself with the less number of digits every time until it'll check them all.
Here is a snippet which might help you to understand the idea:
int countNum(int val)
{
if(!val) return 0;
return countNum(val/10) + ((val % 10) < 5);
}
void countNum(int n, int *c){
if(n != 0){
int num = n % 10;
countNum(n / 10, c);
if(num < 5){
printf("%d", num);
++*c;
}
}
}
int main(){
int num, count = 0;
scanf("%d", &num);
countNum(num, &count);
printf(" - %d\n", count);
return 0;
}
for UPDATE
int rec(int num){
if (num==0) {
return 0;
}
int dg;
dg = rec(num/10);//The order in which you call.
if(num%10<5){
printf("%d", num%10);
dg++;
}
return dg;
}
int main(){
int n;
scanf("%d", &n);
int i,a;
for(i=0;i<n;i++){
scanf("%d", &a);
printf(" - %d\n", rec(a));
}
return 0;
}

Decimal to binary C while dividing by 2

I have to write 2 programs that convert dec to bin. I've finish the 1st one however when I try to run this one it prints out an array of random number not sure why, here is what I have:
#include <stdio.h>
int getNumber();
int dectoBin(int, int binarray[], int);
void printBin(int binary[], int dec);
int main()
{
int M = 8;
int binarray[M];
int dec = getNumber();
printf("The decimal number you entered was: %d", dec);
decToBin(dec, binarray, M);
printBin(binarray, dec);
return 0;
}
int getNumber()
{
int dec;
printf("Enter any a number between 0 and 255: ");
scanf("%d",&dec);
return dec;
}
int decToBin(int dec, int binarray[], int M)
{
int i, j;
for(i=8; i>=0;i--)
{
while(dec != 0)
{
binarray[i]= dec % 2;
dec = dec / 2; binarray[i] = dec;
}
}
return *binarray;
}
void printBin(int binary[], int dec)
{
int i;
if(dec > 255)
{
printf("please use another number");
main();
}
else
{
for(i =8; i >= 0;i--)
{
printf("%d", binary[i]);
printf("\n");
}
}
}
You're setting binarray[i] twice - once correctly (after the modulus statement) and once incorrectly (after dividing dec). So if your decimal number is 65, your second-to-last number would be 32.
You can also make binarray an array of bits rather than numbers. This would have given you a error on compilation and would have perhaps clued you into the logical error.
EDIT: There are a lot of control flow issues with this program. You should check to see if dec > 255 BEFORE calling decToBin otherwise the program will run incorrectly. decToBinary shouldn't return an int - it should return an array of ints (or bits as I suggested) and that is what you should send to printBin. Right now you're returning the pointer to binArray (do you know what pointers are?) decToBin should also return void since it does not perform any calculations.
EDIT 2: As someone else pointed out your array indexes are incorrect, I don't know how you haven't gotten an array out of bounds error. Also, while printing you're going the wrong way: You need to use a for loop that starts at 0 and ends at 7.
Here are some suggestions.
You have dectoBin in the declaration but decToBin in the function call and function definition. Make sure they are all dectoBin or they are all decToBin.
M is not used in decToBin. Feel free to remove it.
I would change getNumber() such that it checks for the range and makes sure that you get a number between 0 to 255 from its return statement. That would eliminate the need to do that check in printBin.
Implementation of decToBin is quite a bit simpler than what you were thinking. The for-loop can be simplified to:
for(i=7; i>=0;i--, dec /= 2)
{
binarray[i]= dec % 2;
}
And finally, implementation of printBin can be a little bit different to make the output more readable. Instead of printing one number at a time, they can all be printed in one line.
Here's what I came up with:
#include <stdio.h>
int getNumber();
int decToBin(int, int binarray[]);
void printBin(int binary[], int dec);
int main()
{
int M = 8;
int binarray[M];
int dec = getNumber();
printf("The decimal number you entered was: %d\n", dec);
decToBin(dec, binarray);
printBin(binarray, dec);
return 0;
}
int getNumber()
{
int dec;
printf("Enter a number between 0 and 255: ");
scanf("%d",&dec);
if( dec < 0 || dec > 255)
{
printf("Please use another number\n");
return getNumber();
}
return dec;
}
int decToBin(int dec, int binarray[])
{
int i;
for(i=7; i>=0;i--, dec /= 2)
{
binarray[i]= dec % 2;
}
return *binarray;
}
void printBin(int binary[], int dec)
{
int i;
printf("The decimal number in binary: ");
for(i=0; i!=8; ++i)
{
printf("%d", binary[i]);
}
printf("\n");
}
A sample execution and output:
~>>./test-07
Enter a number between 0 and 255: 149
The decimal number you entered was: 149
The decimal number in binary: 10010101

Reversing a result

I'm new to C and I'm trying to convert decimal to binary.
The result is giving me an inverse number of what's required.
I tried to apply modulo on the result like I saw on other forums but I still get the same result.
Any help?
#include<stdio.h>
int main()
{
int number;
long int quotient, rem;
printf("Enter a number: ");
scanf("%d", &number);
quotient=number;
while (quotient!=0)
{
quotient=quotient/2;
rem=quotient%2;
printf("%ld", rem%10);
rem/=10;
}
}
I took an advice basing on a Print Function but still not sure if i understand it stills give me the same result. Please have a look.
#include<stdio.h>
void Print(int number,int base)
{
if (number >= base)
Print(number/base,base);
printf("%d",number%base);
}
int main()
{
int number;
long int quotient, rem;
printf("Enter a number: ");
scanf("%d", &number);
quotient=number;
while (quotient!=0)
{
quotient=quotient/2;
rem = quotient%2;
Print(rem, 2);
}
}
Just a small note because i forgot to say and I don't want you to go through the trouble.
The idea os to not use arrays.
Thanks
You can do it the "Last In First Out" way:
void Print(int number,int base)
{
if (number >= base)
Print(number/base,base);
printf("%d",number%base);
}
Then, from main, you can call it with any base between 2 and 10.
you shall various way to solve the problem.
process 1: just do right shift, check shifted result and print decised output.
int main()
{
int n, c, k;
printf("Enter an integer in decimal number system\n");
scanf("%d", &n);
printf("%d in binary number system is:\n", n);
for (c = 31; c >= 0; c--)
{
k = n >> c;
if (k & 1)
printf("1");
else
printf("0");
}
printf("\n");
return 0;
}
I'm trying to convert decimal to binary
You don't have anything decimal past the point you have scanned the input. You have a number. Numbers are not decimal or binary, they are just numbers. scanf has converted a decimal representation of some number to just a number for you.
Once you have a number you want to obtain its binary representstion. Once again, you have nothing decimal at hand.
Now ask yourself whether division by 10 you have found at some dark corner of the Internet could possibly be correct here.
(This answer is intentionally left unfinished)
long int decimalNumber,remainder,quotient;
int binaryNumber[100],i=1,j;
printf("Enter any decimal number: ");
scanf("%ld",&decimalNumber);
quotient = decimalNumber;
while(quotient!=0){
binaryNumber[i++]= quotient % 2;
quotient = quotient / 2;
}
printf("Equivalent binary value of decimal number %d: ",decimalNumber);
for(j = i -1 ;j> 0;j--)
printf("%d",binaryNumber[j]);
Here you go from your own code I was able to correct misleads and provide a correct display of the binary number.
#include<stdio.h>
int main()
{
long int decimal, quotient;
int binarynumber[1024];
const int base = 2;
printf("Enter a number: ");
scanf("%ld", &decimal);
printf("%d in binary: ", decimal);
quotient = decimal;
int i=1;
while (quotient!=0)
{
binarynumber[i++]=quotient%base;
quotient/=base;
}
for(int j=i; j>0; --j){
printf("%d",binarynumber[j]);
}
printf("\n");
return 0;
}
You were correct to have a decimal number variable, I called it decimal to avoid confusion. However, you can just store the input of the decimal number inside of quotient, it will work just the same.
I added the base number variable base, which should be a constant in my opinion, instead of the modulus operator plus base, which is %2 in your code.
You should have a variable, you had rem, binarynumber in this code - to store it all in and then reverse the numbers in this variable like in the for loop provided in the code. I though it better to store it in an array instead of creating a confusion with an additional variable called rem.
I don't entierly know what you wanted to do with rem/=10;, so I worked around that.
You were correct to use long int for the quotient, however, long int in many cases, is the same as int.
On many (but not all) C and C++ implementations, a long is larger than
an int. Most compilers use a 32 bit int which has the same size and representation
as a long. Reference
One more thing, you used to divide by base and store into the quotient (in your code quotient=quotient/2;) before retrieving the modulus answer, which resulted in a incorrect modulus, an incorrect remainder that is (in your code rem=quotient%2;). It retrieved the reminder of the next number.
Hope this is clear.
Try this code.
int number;
printf("Enter a number: ");
scanf("%d", &number);
printf("%d",decimal_binary(number));
int decimal_binary(int n) /* Function to convert decimal to binary.*/
{
int rem, i=1, binary=0;
while (n!=0)
{
rem=n%2;
n/=2;
binary+=rem*i;
i*=10;
}
return binary;
}

Converting decimal to binary in C

The code is giving false answers. İf number equals 42, it turns it to 101010. Ok, it is true. But if number equals 4, it turns it to 99. I didn't find the mistake. How can i fix the code?
#include<stdio.h>
#include<conio.h>
#include<math.h>
int main()
{
int i,digit,number=4;
long long bin= 0LL;
i=0;
while(number>0)
{
digit=number%2;
bin+=digit*(int)pow(10,i);
number/=2;
i++;
}
printf("%d ",bin);
getch();
}
Stop using floating point calculations for this. You are subject to the vagaries of floating point. When I ran your program with my compiler, the output was 100. But I guess your compiler treated the floating point pow differently.
A simple change to make the code behave, and use integer arithmetic only, would be like this:
#include<stdio.h>
#include<conio.h>
#include<math.h>
int main()
{
int digit,number=4;
long long scale,bin= 0LL;
scale=1;
while(number>0)
{
digit=number%2;
bin+=digit*scale;
number/=2;
scale*=10;
}
printf("%lld ",bin);
getch();
}
But I'd rather see the binary built up in a string rather than an integer.
You can use a simpler and easier approach to convert decimal to binary number system.
#include <stdio.h>
int main()
{
long long decimal, tempDecimal, binary;
int rem, place = 1;
binary = 0;
/*
* Reads decimal number from user
*/
printf("Enter any decimal number: ");
scanf("%lld", &decimal);
tempDecimal = decimal;
/*
* Converts the decimal number to binary number
*/
while(tempDecimal!=0)
{
rem = tempDecimal % 2;
binary = (rem * place) + binary;
tempDecimal /= 2;
place *= 10;
}
printf("\nDecimal number = %lld\n", decimal);
printf("Binary number = %lld", binary);
return 0;
}

Resources