float resultInteger = 0.0f;
float power = 1/2.0f;
for (i = highPointPosition+1; i <= highResultIndex; i++, power /= 2
resultInteger += result[i] * power;
power = 1.0f;
for (i = highPointPosition, power = 1.0f; i >= 0; i--, power *= 2)
resultInteger += result[i] * power;
if (carry == 1)
resultInteger += carry * power;
The above code converts binary to floating point number.
I have been given an assignment asking me to convert two floating point numbers to binary and then adding them and then converting the result to float.
In the above code when I perform 3.5 + 5.39 the result should be 8.89, but instead it is 8.889999.
For others like 9.5 + 7.39 the answer is right i.e., 16.89.
Can Anyone help explain why I am encountering such problem?
Binary can't expression 1/10 in decimal accurately, like how base 10 can't expression 1/3 accurately, while base 12 can (1 third is 0.4 in base 12).
Normally, if you want to get better math accuracy, you would use decimal to do the math instead, like this:
decimal x = 2.5M;
decimal y = 1.19M;
Console.WriteLine(x + y);
decimal works because it calculates in base ten, not binary. However, if your professor is asking you to do convert into binary to do the math, then it doesn't matter what the initial type was. It will never be possible to get the correct result with binary.
It happens for the reason that 1/10 can't be expressed accurately in binary system.
You can try the following:
float a = 3.5f;
float b = 5.39f;
Console.WriteLine(Math.Round(a + b, 2));
Console.ReadLine();
Use Math.Round(value, digits), you can get the result you want.
Related
I'm currently work on a certain program (in C# .NET - winforms), and among the things i came across the following problem:
I need to calculate the point (t, f(t)) given that:
f(t) = [Sin(t) / 16*Cos^4(t)]^(1/3), Such that: t: -89.995 -> 89.995. (t is real number).
Note: the value of t is ranges from -89.995 to 89.995.
I use the .NET functions Math.Sin(), Math.Cos(), Math.Pow() for the calculations, the converssions from radians to degrees are correct and all right.
The problem is that for every t < 0 that i put in f(t) i got NaN ( = not a number) from the above functions, and when i calculate it in a standard calculator i get standard correct values.
For examplae: t = -0.9165664, f(t) = -0.1000096, (Taht's the correct result).
but when i use the .NET functions in my program, the result i get for t = -0.9165664 is NaN (= Not a Number), why? it's not an exeption, not dividing by zero or something like that.
The code i use in the program:
float t = -0.9165664;
float numerator = Math.Sin(t * Math.PI / 180.0f);
float denominator = 16.0f * Math.Pow(Math.Cos(t * Math.PI / 180.0f), 4)
float ft = (float)Math.Pow(numerator / denominator, 1.0f / 3.0f));
Note: I can't cahnge the type of ft to double.
When i put any t > 0 in the above code it gives the correct result.
Can someone explain me what wrong or suggest a possible solution?
Thanks for help!!!
The problem is the definition of the Math.Pow function, see the documentation. Since your exponent is fixed and you're looking for the 3rd root as a real number, try something like
float t = -0.9165664;
float numerator = Math.Sin(t * Math.PI / 180.0f);
float denominator = 16.0f * Math.Pow(Math.Cos(t * Math.PI / 180.0f), 4)
float val = numerator / denominator;
float ft = Math.Sign(val) * (float)Math.Pow(Math.Abs(val), 1.0f / 3.0f));
Consider this:
double x,y;
x =120.0;
y = 0.05;
double z= x % y;
I tried this and expected the result to be 0, but it came out 0.04933333.
However,
x =120.0;
y = 0.5;
double z= x % y;
did indeed gave the correct result of 0.
What is happening here?
I tried Math.IEEERemainder(double, double) but it's not returning 0 either. What is going on here?
Also, as an aside, what is the most appropriate way to find remainder in C#?
Because of its storage format, doubles cannot store every values exactly as is is entered or displayed. The human representation of numbers is usually in decimal format, while doubles are based on the dual system.
In a double, 120 is stored precisely because it's an integer value. But 0.05 is not. The double is approximated to the closest number to 0.05 it can represent. 0.5 is a power of 2 (1/2), so it can be stored precisely and you don't get a rounding error.
To have all numbers exactly the same way you enter / display it in the decimal system, use decimal instead.
decimal x, y;
x = 120.0M;
y = 0.05M;
decimal z = x % y; // z is 0
You could do something like:
double a, b, r;
a = 120;
b = .05;
r = a - Math.floor(a / b) * b;
This should help ;)
I believe if you tried the same with decimal it would work properly.
http://en.wikipedia.org/wiki/Floating_point#Accuracy_problems can help you understand why you get these "strange" results. There's a particular precision that floating point numbers can have. Just try these queries and have a look at the results:
0.5 in base 2
0.05 in base 2
Modulus should only be used with integer. The remainder come from an euclidean division. With double, you can have unexpected results.
See this article
This is what we use.. :)
public double ModuloOf(double v1, double v2)
{
var mult = 0;
//find number of decimals
while (v2 % 1 > 0)
{
mult++;
v2 = v2 * 10;
}
v1 = v1 * Math.Pow(10, mult);
var rem = v1 % v2;
return rem / Math.Pow(10, mult);
}
Learning C#, Math equation not resulting as expected.
This is apart of my homework. I do not understand why the result are not coming out as them should..
First equation
m=2
n=1
int sideA = (m^2) - (n^2);
result -3
Second equation
x1=2
x2=7
float Xmid = (x1 + x2)/2;
result 4
This is because in C# ^ means XOR, not "raised to the power of". To square a number, use
Math.Pow(x, 2)
or simply
x * x
Also dividing integers truncates the fractional part. Use decimal, double, or float to get 3.5 as the midpoint of 3 and 4:
float x1=2
float x2=7
float Xmid = (x1 + x2)/2;
Your first line of code:
int sideA = (m^2) - (n^2);
Is basically m XOR 2 minus n XOR 2. XOR is a bitwise operator that results in the bits where one is true but not both. For more information on the exclusive OR operator, consult Wikipedia. If you're trying to raise m to the power of 2, try something like:
int sideA = Math.Pow(m, 2) - Math.Pow(n, 2);
Your second line of code:
float Xmid = (x1 + x2)/2;
Is (2 + 7) which is 9, divided by the integer 2 which is 4.5, however because dividing an integer by another integer will always result in an integer, only the integer portion of the result will be kept. The fact that you're assigning this expression to a float is irrelevant.
You might want to try:
float Xmid = (x1 + x2)/2.0;
or:
float Xmid = (x1 + x2)/2f;
or declare x1 and x2 as floats, both which will yield 4.5.
let suppose dis.text = 2, prc.text = 100, I am using these codes.It Should be
net_prc.text = 98.But its giving me -100.Can anybody tell me why?,And how can i get correct
discounted percentage??
private void net_prcTabChanged(object sender, EventArgs e)
{
int d;
int di;
int i;
d = Convert.ToInt32(dis.Text);
i = Convert.ToInt32(prc.Text);
di = -((d / 100) * i) + i;
net_prc.Text = di.ToString();
}
Try (d / 100.0) to force it to use floating point arithmetic
di = -((d / 100) * i) + i;
All values in this statement are Integers. You are going to be computing arithmetic with decimal places, and you need to increase the precision of your variables to a double or a float. Instead, add a decimal place to one of the values in the equation. This will force all values into doubles.
This is a process called Arithmetic Promotion. It is where, at run time, the precision of every variable in an equation is increased to the size of the most precise variable.
Proper way to do it would be, changing the datatype of di to float
di = (d * 100) / i;
C# has an odd way of doing maths, because your numbers are cast as integers, you can only do integer math with them. you need to initially have them as float or as double so you can do float math or anything at all that requires a decimal place within the calculations.
Even dis.text = 1.5
private void net_prcTabChanged(object sender, EventArgs e)
{
double d;
double di;
double i;
d = Convert.ToDouble(dis.Text);
i = Convert.ToDouble(prc.Text);
di = -((d * 100.0) / i ) + i;
net_prc.Text = di.ToString();
}
Your division, d / 100, is a division of integers, and it returns an integer, probably 0 (zero). This is certainly the case with your example d = 2.
Addition: If you really want to do this with integers (rather than changing to decimal or double like many other answers recommend), consider changing the sub-expression
((d / 100) * i)
into
((d * i) / 100)
because it will give you a better precision to do the division as the last operation. With the numbers of your example, d=2 and i=100, the first sub-expression will give 0*100 or 0, while the changed sub-expression yields 200/100 which will be 2. However, you will not get rounding to nearest integer; instead you will get truncating (fractional part is discarded no matter if it's close to 1).
I was very surprised when I found out my code wasn't working so I created a console application to see where the problem lies and I've got even more surprised when I saw the code below returns 0
static void Main(string[] args)
{
float test = 140 / 1058;
Console.WriteLine(test);
Console.ReadLine();
}
I'm trying to get the result in % and put it in a progress(meaning (140 / 1058) * 100) bar on my application,the second value(1058) is actually ulong type in my application,but that doesn't seem to be the problem.
The question is - where the problem is?
You are using integer arithmetic and then converting the result to a float. Use floating-point arithmetic instead:
float test = 140f / 1058f;
The problem is that you are dividing integers and not floats. Only the result is a float. Change the code to be the following
float test = 140f / 1058f;
EDIT
John mentioned that there is a variable of type ulong. If that's the case then just use a cast opeartion
ulong value = GetTheValue();
float test = 140f / ((float)value);
Note, there is a possible loss of precision here since you're going from ulong to float.
This will work the way you expect ...
float test = (float)140 / (float)1058;
By the way, your code works fine for me (prints a 0.1323251 to the console).
The division being performed is integer division. Replace
float test = 140 / 1058;
with
float test = 140f / 1058;
to force floating-point division.
In general, if you have
int x;
int y;
and want to perform floating-point division then you must cast either x or y to a float as in
float f = ((float) x) / y;