Why double, long double are always showing 0 as output? - c

I am writing code to find the distance of a point(25,40000) from a fixed point(47,132000). The distance always printed to be 0.0000.
I have tried checking other combinations, giving smaller values of points, and printing them with %d, it works great.
But with %ld,%lf,%Lf something is not fine. Kindly help.
#include<stdio.h>
#include<math.h>
int main()
{
int x=25,y=40000;
//printf("Enter x,y");
//scanf(%d %d,&x,&y)
long double dist;
dist=sqrt((47-x)*(47-x)+(132000-y)*(132000-y));
printf(" x= %d y=%d dist=%Lf\n",x,y,dist);
return 0;
}

Integer overflow takes place in your code. The below code works -
int main()
{
long long int x=25,y=40000; //int was overflowing and causing you error
long double dist;
dist=sqrt((47-x)*(47-x)+(132000-y)*(132000-y)); //this will safely compute within range and return the desired result
printf("After distance\n");
printf(" x= %lld y=%lld dist=%Lf\n",x,y,dist);
return 0;
}
You were getting wrong output(-nan when I tried out ) because the expression value inside sqrt() was overflowing and becoming negative. (132000-y)*(132000-y) won't fit in an integer range and give negative value. Since, negative square root is not defined, sqrt() returned nan as the result. Changing the type of y to long long int will solve the error.
Hope this helps !

Related

Wrong decimal result when adding and dividing numbers in loop

#include<stdio.h>
int main()
{
int n,i;
float sum=0;
scanf("%d",&n);
for(i=1;i<=n;i++)
{
printf("1/%d +",i);
sum=sum+1/i;
}
printf("= %f",sum);
return 0;
}
In this code I've kept the sum variable float to see the values after decimal. But the result doesn't appear to be correct. 000000 is shown after decimal. Why is this happening? What should I do to get the correct value without changing other variable's datatype? When I change other variables to float datatype,the answer remains correct.
Because both 1 and i are integers, the expression 1/i is evaluated as integer.
Therefore, if i > 1 then 1/i == 0.
You can solve this using float(1)/i or 1/float(i) or float(1)/float(i).

why the value of sum is coming out to be negative? [duplicate]

This question already has answers here:
Sum of positive values in an array gives negative result in a c program
(4 answers)
Closed 4 years ago.
I have written the following c code to find the sum of first 49 numbers of a given array, but the sum is coming out to be negative.
#include<stdio.h>
int main()
{
int i;
long int sum=0;
long int a[50]={846930887,1681692778,1714636916, 1957747794, 424238336, 719885387, 1649760493, 596516650, 1189641422, 1025202363, 1350490028, 783368691, 1102520060, 2044897764, 1967513927, 1365180541, 1540383427, 304089173, 1303455737, 35005212, 521595369, 294702568, 1726956430, 336465783, 861021531, 278722863, 233665124, 2145174068, 468703136, 1101513930, 1801979803, 1315634023, 635723059, 1369133070, 1125898168, 1059961394, 2089018457, 628175012, 1656478043, 1131176230, 1653377374, 859484422, 1914544920, 608413785, 756898538, 1734575199, 1973594325, 149798316, 2038664371, 1129566414};
for(i=0;i<49;i++)
{
sum=sum+a[i];
printf("sum is : %ld\n",sum);
}
printf("\nthe total sum is %ld",sum);
}
i don't know why it is coming so?please help.
Using long long instead of long, the program works:
Ouput: 56074206897
Reason
Range of long: -2^31+1 to +2^31-1
Range of long long: -2^63+1 to +2^63-1
As you can see 2^31-1 = 2147483647 <
56074206897; but 2^63-1 = 9,223,372,036,854,775,807 > 56074206897
This leads to overflow. According to the C standard, the result of signed integer overflow is undefined behavior. What that means is that if this condition ever happens at runtime, the compiler is allowed to make your code do anything. Your program could crash, or produce the wrong answer, or have unpredictable effects on other parts of your code, or it might silently do what you intended.
In your case it is overflowing the maximum value of long int on your system. Because long int is signed, when the most significant bit gets set, it becomes a negative number.
I didn't actually add them up, but just looking at them, I'd say its a pretty safe guess that you are running into an integer overflow error.
A long int has a maximum size of about 2 billion (2^31). If you add more than that, it'll look back around and go to -2^31.
You'll need to use a data type that can hold more than that if you want to sum up those numbers. Probably a long long int should work. If you're sure it'll always be positive, even better to use an unsigned long long int.
As long int has maximum range upto 2,147,483,647, and the value of sum is more than the range.So, it is coming as negative value. You can use the following code...
#include<stdio.h>
int main()
{
int i;
long long int sum=0; //Taking long long int instead of long int
int a[50]={846930887,1681692778,1714636916, 1957747794, 424238336,
719885387, 1649760493, 596516650, 1189641422, 1025202363, 1350490028,
783368691, 1102520060, 2044897764, 1967513927, 1365180541, 1540383427,
304089173, 1303455737, 35005212, 521595369, 294702568, 1726956430,
336465783, 861021531, 278722863, 233665124, 2145174068, 468703136,
1101513930, 1801979803, 1315634023, 635723059, 1369133070, 1125898168,
1059961394, 2089018457, 628175012, 1656478043, 1131176230, 1653377374,
859484422, 1914544920, 608413785, 756898538, 1734575199, 1973594325,
149798316, 2038664371, 1129566414};
for(i=0;i<49;i++)
{
sum=sum+a[i];
printf("sum is : %lld\n",sum);
}
printf("\nTotal sum is %lld",sum);
}
As Vlad from Moscow said this is a overflow issue, which made an undefined behavior. In you system (long int sum) sum does not have capacity to hold the total value. Not sure but you can use long long int sum =0;(after C99). If it still cannot work properly, search for "BigInteger" implement.

Why the factorial of 153 has failed in following program

I have created a myfun.h header file with two functions in it. A factorial function and amstrong function and a myfun.c file
Here is myfun.h program
void factorial(int n,int *fact)
{
int i;
*fact=1;
for(i=1;i<=n;i++)
*fact=*fact*i;
}
amstrong(int n)
{
int sum=0,num,rem,cube;
num=n;
while(num>0)
{
rem=num%10;
cube=rem*rem*rem;
num=num/10;
sum=sum+cube;
}
if(sum==n)
return(1);
else
return(0);
}
Here is the myfun.c program
#include<stdio.h>
#include "myfun.h"
int main()
{
int num,rev,f,code;
printf("Enter number :");
scanf("%d",&num);
code=amstrong(num);
if(code==1)
printf("\nNumber is amstrong\n");
else
printf("Number is not amstrong\n");
factorial(num,&f);
printf("Factorial of %d is %d ",num,f);
getch();
}
In this the amstrong function is working fine.But the factorial function is giving output 0. I haven't tried it without removing pointer variable. But if i want to run it with pointer variable then what changes i need to do?
The output of program is
Enter number: 153
Number is amstrong
Factorial of 153 is 0
153! = 2.01 E+269.
In case unsigned long long is 64 bits, it can hold a maximum value of 2^64 = 18.45 E+19.
You will need to use some form of "big int" library to calculate huge numbers like these.
This is happening because there is a every data type can hold upto a certain number. The reason that you are getting wrong answer is because the fact of 153 would be bigger then what an int variable can hold. It should work fine for smaller values.
Edit
To store larger numbers you can use long long int data type.
The minimum data type ranges you can use are:
short int and int: -32,767 to 32,767
unsigned short int and unsigned int: 0 to 65,535
long int: -2,147,483,647 to 2,147,483,647
unsigned long int: 0 to 4,294,967,295
int alone cannot store the value given by fact (153). Use smaller values for your case, otherwise change the type: use a long long int instead.
sizeof(long double) = 12bytes on a machine running 32-bit linux. The output can be printed by using %LE in printf. Output will be in exponential form.
EDIT
factorial(20) : 2432902008176640000 when using long long int
This is maximum you can get with long long int type of variable.
For greater ranges use long double.

To print the answer from the series -> x^3 - x^5 + x^7 - x^9 +

#include<stdio.h>
#include<conio.h>
#include<math.h>
int main()
{
int x,n;
float sum=0;
printf("Length and Value");
scanf("%d%d",&n,&x);
for(int i=1;i<=n;i++)
{
sum+=(pow(x,2*i+1) * pow(-1,i+1));
}
printf("%f",sum);
return 0;
}
I'm trying to solve this series in C language. Am I doing something wrong in the above code?
Yes, you're a bit wrong. In your code
printf("%f",sum);
sum is an int and using %f to print the value of an int is undefined behaviour.
The function pow() returns a double. You may want to change your sum to type double.
If you don't mind using your own version, a better looking implementation, without using pow() will be
Store the existing value.
Multiply by x * x on each iteration
Take care of -ve sign for even numbered iteration.
First things first, your printf has the wrong format specifier for an int: use %d instead. But for non-integral x, you'll want to refactor to a double anyway, so %f will probably be retained.
Secondly, don't use pow: it will not be precise (probably implemented as exp(log)) and you don't need to evaluate the power from scratch for each term.
Keep a running power: i.e. compute x * x * x initially, then successively multiply that by x * x for subsequent terms. Don't forget to alternate the signs: you can do that by multiplying by -1.
you are trying to find x^3,x^5 that is power in odd. so do a little change in your for loop. write this instead of your code. and if you give a large x or n value then it is preferable to declare sum as a long data type
#include<stdio.h>
#include<conio.h>
#include<math.h>
int main()
{
int x,n;
long sum=0;
printf("Length and Value");
scanf("%d%d",&n,&x);
for(int i=2;i<=n;i+=2)
{
sum+=(pow(x,i+1) * pow(-1,i));
}
printf("%l",sum);
return 0;
}
First of all, you are trying to evaluate a series that diverges for all points outside and on the circle of radius one (as a complex series). If you use an int for x, you will get each time values bigger and bigger, oscillating around 0. Try it with numbers of ||x|| < 1 (this means double or float for x)
All the other answers posted are also usefull to get sooner to the expected value.

Multiplication of float with int in c

#include <stdio.h>
int main(){
float var = 0.612;
printf("%f\n",var);
printf("%f\n",var*100);
return 0;
}
o/p
0.612000
61.199997
I found that for JavaScript, we have .tofixed() method.
How do we get a fix for this in C?
You can specify the precision when printing:
printf("%.3f\n", 100 * var);
Since the exact number you're having probably isn't representable in the float itself, there is no operation you can do on the number itself to "remove" the decimals, it's all a matter of how you choose to present the data.

Resources