I am using python 2.7.6. When I type this into the interpreter
>>> 0.135-0.027
0.10800000000000001
Whereas it should be just
0.108
This causes problem when comparing things, for example I want to compare
>>> 0.135-0.027 <= 0.108
False
I want this to give answer as True. Do I have to use a special package that will handle floats properly? Is there a way to fix this another way? For example we can force floating division with
from __future__ import division
Is there a similar solution to this problem?
There are various things you can do, but each has its own advantages and disadvantages.
The basic problem is that conversion from decimal to any finite binary representation involves rounding. If you were to use IEEE quadruple precision, for example, these cases would be rarer, but would still occur.
You could use a decimal library or an arbitrary precision library, but you may be unwilling to pay the cost in runtime for using them if you have to do trillions of these calculations.
In that case, you have to ask yourself the question, “How accurately do I really know these numbers?” Then you can consider, “Is it permissible for 0.135-0.027 <= 0.108 to be considered true?” In most cases, the answer to these is “not that accurately” and “yes” and your problem is solved. You might be uncomfortable with the solution, but it's swings and roundabouts: the errors are going to occur “both ways” (in the sense that it sometimes the comparison is going to fail when it should succeed, and sometimes it is going to succeed when it should fail).
If failing one way is perfectly OK, but failing the other way is absolutely not, you can either change the rounding mode of your hardware (to suit the bias you want), or you can add/subtract a ULP (to suit the bias you want).
For example, consider the following (sorry for the C, but I'm sure you get the idea):
double add_ulp(double x) {
union {
double x;
unsigned sign : 1;
unsigned expo : 11;
unsigned long mant : 52;
} inc;
inc.x = x;
inc.mant = 0;
if (inc.expo >= 52 ) {
inc.expo -= 52;
return x+inc.x;
}
return x;
}
You can use this like this:
if( x-y <= add_ulp(z) ) {
// ...
}
And it will give you the answer you want in your case, but it will bias your results in general. If that's the bias you want, it isn't a problem, but if it's not, it's worse than the problem you currently have.
Hope this helps.
This might help:
https://pythonhosted.org/bigfloat/
You can control the precision with this as well.
Related
Also is a<=b similar in performance to a<b or is it two times.
Consider these three scenarios:
for (int i =0; i <= 10; i++) {
// Some operations here
}
for (int i =0; (i < 10) OR (i == 10); i++) {
// Some operations here
}
for (int i =0; i <10; i++) {
// Some operations here
}
How would you compare these three?
It depends on programming language, hardware and compiler, but, if you are about C++ over common x86 CPU and compiler that can not optimize this statement, the difference is about assebmly code generation.
On Assembler level, comparison is subtraction with further flags check. a <= b may become something like that:
cmp eax, ebx
jle a_le_b
We suppose that variables are in registers already to simplify the example. You see, we need 2 instruction only.
(a<b) | (a==b) literally means this:
cmp eax, ebx
jl a_le_b
cmp eax, ebx
je a_le_b
Again, here I translated the C++ to assembler without any optimization, just "as is". If compiler has optimization enabled, it will most probably generate the same code for both statements.
Now, in C++ the operators may be overloaded. It means that <= (theoretically) can perform completely different operations of different cost that < and =. However, in practice usually <= will be implemented exactly like call to < followed by call to == or vice versa.
Conclusion: in practice, for optimized compiler on common processor type and semantically correct class that calls comparison operator, you will not have any observable difference. However, semantics of these 2 statements are not exactly the same, so theoretically it is even possible that a <= b will give different result from a < b | a == b.
Taking your question literally, the answer is O(1) for both.
But assuming that you're more interested in the execution time, the answer depends on whether the code is interpreted of compiled. Any modern compiler will optimise them both to the same code. An interpreter will take twice as long doing both checks for the equals and greater-than cases since the first test will fail and it will need to test the second.
Complexity is generally expressed in big-O notation. Even if the second case would be O(2) (compilers might disagree), then the complexities would still be the same because O(2) is exactly the same as O(1).
Whether one takes twice as much as the other is irrelevant for complexity, they all have constant complexity, as independent of the value of a or b they take a fixed amount of operations.
In case you worry about performance, note that the compiler knows what expressions are equivalent and it is likely better than humans to pick the one that is cheapest.
What is the Time Complexity difference between "a<=b" and "(a<b) OR (a==b)"?
Complexity analysis applies to algorithms. Relational comparisons are not algorithms, so their complexity cannot be analysed. We can only analyse an algorithm used to implement such comparison. What algorithm can be used depends on what types are compared. The answer also depends on whether we consider worst, best or average case.
<= can usually be implemented as (a<b) OR (a==b). In such case the complexity of <= cannot be worse than the complexity of (a<b) OR (a==b) unless it has been implemented sub-optimally. The complexity of <= is usually the same as the worse complexity of either a<b or a==b. Most often, all of these three have the same asymptotic complexity. But this depends on the type of the compared objects.
int i =0; (i < 10) OR (i == 10)
int i =0; i <= 10
The asymtotic complexity of these comparisons is exactly the same: It is constant. In fact, the size of int is constant for any system, so there is no input that can grow, and so asymptotic analysis would be pointless.
In the languages I have tested, - (x div y ) is not equal to -x div y; I have tested // in Python, / in Ruby, div in Perl 6; C has a similar behavior.
That behavior is usually according to spec, since div is usually defined as the rounding down of the result of the division, however it does not make a lot of sense from the arithmetic point of view, since it makes div behave in a different way depending on the sign, and it causes confusion such as this post on how it is done in Python.
Is there some specific rationale behind this design decision, or is just div defined that way from scratch? Apparently Guido van Rossum uses a coherency argument in a blog post that explains how it is done in Python, but you can have coherency also if you choose to round up.
(Inspired by this question by PMurias in the #perl6 IRC channel)
Ideally, we would like to have two operations div and mod, satisfying, for each b>0:
(a div b) * b + (a mod b) = a
0 <= (a mod b) < b
(-a) div b = -(a div b)
This is, however, a mathematical impossibility. If all the above were true, we would have
1 div 2 = 0
1 mod 2 = 1
since this is the unique integer solution to (1) and (2). Hence, we would also have, by (3),
0 = -0 = -(1 div 2) = (-1) div 2
which, by (1), implies
-1 = ((-1) div 2) * 2 + ((-1) mod 2) = 0 * 2 + ((-1) mod 2) = (-1) mod 2
making (-1) mod 2 < 0 which contradicts (2).
Hence, we need to give up some property among (1), (2), and (3).
Some programming languages give up (3), and make div round down (Python, Ruby).
In some (rare) cases the language offers multiple division operators. For instance, in Haskell we have div,mod satisfying only (1) and (2), similarly to Python, and we also have quot,rem satisfying only (1) and (3). The latter pair of operators rounds division towards zero, at the price of returning negative remainders, e.g., we have (-1) `quot` 2 = 0 and (-1) `rem` 2 = (-1).
C# also gives up (2), and allows % to return a negative remainder. Coherently, integer division rounds towards zero. Java, Scala, Pascal, and C, starting from C99, also adopt this strategy.
Floating-point operations are defined by IEEE754 with numeric applications in mind and, by default, round to the nearest representable value in a very strictly-defined manner.
Integer operations in computers are not defined by general international standards. The operations granted by languages (especially those of the C family) tend to follow whatever the underlying computer provides. Some languages define certain operations more robustly than others, but to avoid excessively difficult or slow implementations on the available (and popular) computers of their time, will choose a definition that follows its behaviour quite closely.
For this reason, integer operations tend to wrap around on overflow (for addition, multiplication, and shifting-left), and round towards negative infinity when producing an inexact result (for division, and shifting-right). Both of these are simple truncation at their respective end of the integer in two's-complement binary arithmetic; the simplest way to handle a corner-case.
Other answers discuss the relationship with the remainder or modulus operator that a language might provide alongside division. Unfortunately they have it backwards. Remainder depends on the definition of division, not the other way around, while modulus can be defined independently of division - if both arguments happen to be positive and division rounds down, they work out to be the same, so people rarely notice.
Most modern languages provide either a remainder operator or a modulus operator, rarely both. A library function may provide the other operation for people who care about the difference, which is that remainder retains the sign of the dividend, while modulus retains the sign of the divisor.
Because the implication of integer division is that the full answer includes a remainder.
Wikipedia has a great article on this, including history as well as theory.
As long as a language satisfies the Euclidean division property that (a/b) * b + (a%b) == a, both flooring division and truncating division are coherent and arithmetically sensible.
Of course people like to argue that one is obviously correct and the other is obviously wrong, but it has more the character of a holy war than a sensible discussion, and it usually has more to do with the choice of their early preferred language than anything else. They also often tend to argue primarily for their chosen %, even though it probably makes more sense to choose / first and then just pick the % that matches.
Flooring (like Python):
No less an authority than Donald Knuth suggests it.
% following the sign of the divisor is apparently what about 70% of all students guess
The operator is usually read as mod or modulo rather than remainder.
"C does it"—which isn't even true.1
Truncating (like C++):
Makes integer division more consistent with IEEE float division (in default rounding mode).
More CPUs implement it. (May not be true at different times in history.)
The operator is read modulo rather than remainder (even though this actually argues against their point).
The division property conceptually is more about remainder than modulus.
The operator is read mod rather than modulo, so it should follow Fortran's distinction. (This may sound silly, but may have been the clincher for C99. See this thread.)
"Euclidean" (like Pascal—/ floors or truncates depending on signs, so % is never negative):
Niklaus Wirth argued that nobody is ever surprised by positive mod.
Raymond T. Boute later argued that you can't implement Euclidean division naively with either of the other rules.
A number of languages provide both. Typically—as in Ada, Modula-2, some Lisps, Haskell, and Julia—they use names related to mod for the Python-style operator and rem for the C++-style operator. But not always—Fortran, for example, calls the same things modulo and mod (as mentioned above for C99).
We don't know why Python, Tcl, Perl, and the other influential scripting languages mostly chose flooring. As noted in the question, Guido van Rossum's answer only explains why he had to choose one of the three consistent answers, not why he picked the one he did.
However, I suspect the influence of C was key. Most scripting languages are (at least initially) implemented in C, and borrow their operator inventory from C. C89's implementation-defined % is obviously broken, and not suitable for a "friendly" language like Tcl or Python. And C calls the operator "mod". So they go with modulus, not remainder.
1. Despite what the question says—and many people using it as an argument—C actually doesn't have similar behavior to Python and friends. C99 requires truncating division, not flooring. C89 allowed either, and also allowed either version of mod, so there's no guarantee of the division property, and no way to write portable code doing signed integer division. That's just broken.
As Paula said, it is because of the remainder.
The algorithm is founded on Euclidean division.
In Ruby, you can write this rebuilding the dividend with consistency:
puts (10/3)*3 + 10%3
#=> 10
It works the same in real life. 10 apples and 3 people. Ok you can cut one apple in three, but going outside the set integers.
With negative numbers the consistency is also kept:
puts (-10/3)*3 + -10%3 #=> -10
puts (10/(-3))*(-3) + 10%(-3) #=> 10
puts (-10/(-3))*(-3) + -10%(-3) #=> -10
The quotient is always round down (down along the negative axis) and the reminder follows:
puts (-10/3) #=> -4
puts -10%3 #=> 2
puts (10/(-3)) #=> -4
puts 10%(-3) # => -2
puts (-10/(-3)) #=> 3
puts -10%(-3) #=> -1
This answer addresses a sub-part of the question that the other (excellent) answers didn't explicitly address. You noted:
you can have coherency also if you choose to round up.
Other answers addressed the choice between rounding down (towards -∞) and truncating (rounding towards 0) but didn't compare rounding up (towards ∞).
(The accepted answer touches on performance reasons to prefer rounding down on a two's-complement machine, which would also apply in comparison to rounding up. But there are more important semantic reasons to avoid rounding up.)
This answer directly addresses why rounding up is not a great solution.
Rounding up breaks elementary-school expectations
Building on an example from a previous answer's, it's common to informally say something like this:
If I evenly divide fourteen marbles among three people, each person gets four marbles and there are two marbles left over.
Indeed, this is how many students are first taught division (before being introduced to fractions/decimals). A student might write 14 ÷ 3 = 4 remainder 2. Since this is introduced so early, we'd really like our div operator to preserve this property.
Or, put a bit more formally, of the three properties discussed in the top-voted answer, the first one ((a div b) × b + (a mod b) = a) is by far the most important.
But rounding up breaks this property. If div rounds up, then 14 div 3 returns 5. This means that the equation above simplifies to 15 + (13 mod 4) = 13 – and that's not true for any definition of mod. Similarly, the less-formal/elementary-school approach is also out of luck – or at least requires introducing negative marbles: "Each person gets 5 marbles and there are negative one marbles left over".
(Rounding to the nearest integer also breaks the property when, as in the example above, that means rounding up.)
Thus, if we want to maintain elementary expectations, we cannot round up. And with rounding up off the table, the coherency argument that you linked in the question is sufficient to justify rounding down.
Being somehow surprised seeing things like this work:
float f = 10.25f;
int i = (int)f;
// Will give you i = 10
What is the gain?
OTOH 10.25 is quite a different thing than 10, which will be agreed, bad things might happen from such a soft conversion.
Which languages raise an error instead?
Would expect someting like: "Error: Can't represent 10.25 as an integer".
WRT to answers given meanwhile: Yes, it might considered reliable the way a function like "round" is. But not straight WRT to integrity of data/information to be expected from cast.
Maybe a function "truncate" which defaults to behavior of "int" would make a better choice?
It is precisely the
(int)f
that tells that the programmer is aware of what he is doing, while silently cutting off the fractional part and storing the rest in an integer is forbidden in most programming languages.
By the way, it is not just that the fractional part is cut off. It is also that a floating point number can have a value so large that it can't possibly be represented as an int. Consider:
(int) 1e20f
The statement int i = (int)f; explicitly says "Please take my float f and make it into int". This is certainly something I quite often find a useful thing to do - why wouldn't you want to be able to convert a float value from a calculation of some sort to an integer? The cast (int) will tell the compiler that "I really want this to be an integer", just like in C you can do char *p = (char *)1234567; - a typecast is there to tell the compiler "I really know what I'm doing".
If you do int i = f; or int i = 10.25; the compiler will still do what you "asked for" - convert the float value to an integer. It will probably issue a warning to say "You are converting a float to int", if you enable the appropriate warnings.
C and C++ are languages that require you to understand what you are doing, and what the consequences are - some other languages put more "barriers" in place to prevent such things, but that often means that the compiler has to add extra code to check things at runtime - C and C++ are designed to be "fast" languages.
It's a bit like driving a car, putting the car in reverse when there is a wall right behind, and stepping on the gas, will probably cause the car to crash into the wall - if that's not what you want, then "don't do that".
Firstly, the conversion is most definitely "reliable", as in "it will always do the same thing".
Whether you want to do that or not is up to you. In general the C/C++ languages are designed to give the programmer a lot of low-level power, and that means that the programmer needs to know what they are doing. If a float-to-int conversion surprises you then you need to think harder.
In fact, GCC has an option -Wconversion that will highlight cases like this. It isn't enabled by default, and is not part of -Wall or -Wextra (presumably because the behaviour is well understood and "expected" by most programmers), but the option is there if you need it.
Except that it won't give a warning, in this case, because your code includes an explicit cast (int), so the compiler assumes you did it deliberately.
This gives a warning (with -Wconversion):
int i = f;
This does not:
int i = (int)f;
Converting to an integer is useful in cases where you are working with complex data, but ultimately need to convert this data to an int to do something with it. Think of offsets in arrays, or pixels on a screen
Think of drawing a circle on the screen. There does not exist a fraction of a pixel (so the coordinates are ints), but you cannot calculate the coordinates of the pixel with just ints (sinus works with pi and other floats).
I've been experimenting with the standard python math module and have come across some subtle difficulties. For example, I'm noticing the following behavior concerning indeterminate forms:
0**0
>>> 1
def inf():
return 1e900
# Will return inf
inf()**inf()
>>> inf
And other anomalies of the sort. I'm writing a calculator, and I'd like to have it be mathematically accurate. Is there something I can do about this? Or, is there some way to circumvent this? Thanks in advance.
There's nothing wrong with your first example. 0**0 is often defined to be 1.
The second example is all to do with precision of doubles. 1E900 exceeds the maximum positive value of a (most likely 64-bit) double. If you want doubles outside of that range, you'll have to look into libraries. Fortunately Python has one built-in: the decimal module.
For example:
from decimal import Decimal
d = Decimal('1E900')
f = d + d
print(f)
>>> 2E900
According to Wolfram (quoting Knuth) while 0**0 is indeterminate, it's sometimes given as 1. This is because holding the statement 'x**0 = 1' to be true in all cases is in some cases useful. Even more interestingly Python will consider NaN**0 to be 1 as well.
http://mathworld.wolfram.com/Power.html
In the case of infinity**infinity, you're not really dealing with the mathematical concept of infinity here (where that would be undefined), but rather a number that's too large and has overflowed. As such all that statement is saying is that a number that's huge to the power of another number that's huge is still a number that's huge.
Edit: I do not think it is possible to overload a built in type (such as float) in Python so overloading the float.__pow__(x,y) operator directly. What you could possibly do is define your own version of float.
class myfloat(float):
def __pow__(x,y):
if(x==y==0):
return 'NaN'
else:
return float.__pow__(x,y)
m = myfloat(0)
m**0
Not sure if that's exactly what you're looking for though.
Well returning NaN for 0**0 is almost always useless and lots of algorithms avoid special cases if we assume 0**0 == 1. So while it may not be mathematically perfect - we're talking about IEEE-754 here, mathematical exactness is really the least of our problems [1]
But if you want to change it, that's rather simple. The following works as expected in Python 3.2:
def my_pow(x, y):
if y == 0: return 'NaN'
return float.__pow__(float(x), y)
pow = my_pow
[1] The following code can theoretically execute the if branch with x86 CPUs (well at least in C and co):
float x = sqrt(y);
if (x != sqrt(y)) printf("Surprise, surprise!\n");
I was just bitten by the following scenario:
>>> -1 ** 2
-1
Now, digging through the Python docs, it's clear that this is intended behavior, but why? I don't work with any other languages with power as a builtin operator, but not having unary negation bind as tightly as possible seems dangerously counter-intuitive to me.
Is there a reason it was done this way? Do other languages with power operators behave similarly?
That behaviour is the same as in math formulas, so I am not sure what the problem is, or why it is counter-intuitive. Can you explain where have you seen something different? "**" always bind more than "-": -x^2 is not the same as (-x)^2
Just use (-1) ** 2, exactly as you'd do in math.
Short answer: it's the standard way precedence works in math.
Let's say I want to evaluate the polynomial 3x3 - x2 + 5.
def polynomial(x):
return 3*x**3 - x**2 + 5
It looks better than...
def polynomial
return 3*x**3 - (x**2) + 5
And the first way is the way mathematicians do it. Other languages with exponentiation work the same way. Note that the negation operator also binds more loosely than multiplication, so
-x*y === -(x*y)
Which is also the way they do it in math.
If I had to guess, it would be because having an exponentiation operator allows programmers to easily raise numbers to fractional powers. Negative numbers raised to fractional powers end up with an imaginary component (usually), so that can be avoided by binding ** more tightly than unary -. Most languages don't like imaginary numbers.
Ultimately, of course, it's just a convention - and to make your code readable by yourself and others down the line, you'll probably want to explicitly group your (-1) so no one else gets caught by the same trap :) Good luck!
It seems intuitive to me.
Fist, because it's consistent with mathematical notaiton: -2^2 = -4.
Second, the operator ** was widely introduced by FORTRAN long time ago. In FORTRAN, -2**2 is -4, as well.
Ocaml doesn't do the same
# -12.0**2.0
;;
- : float = 144.
That's kind of weird...
# -12.0**0.5;;
- : float = nan
Look at that link though...
order of operations