Is there a standard library function which will set a minimum value to a division operation, for example:
min(1, a/b)
This will ensure that min value of operation above will always be 1, never 0.
Such as:
min(1, 1/5)
1
Also, how do I round up a division:
round_up(1/5) = 1
I always get "0" when I divide 1/5, even with ceil function:
math.ceil(1/5)
0
If you want to use floating point division as default, you can do from __future__ import division:
>>> 1/5
0
>>> from __future__ import division
>>> 1/5
0.2
>>> math.ceil(1/5)
1.0
If you need the result to be of integer type, e.g. for indexing, you can use
int(math.ceil(1/5))
The result of 1/5 is an integer already. If you want the floating point version you need to do 1.0/5. The math.ceil function will then work as you expect: math.ceil(1.0/5) = 1.0.
If you're working with variables instead of constants, use the float(x) function to convert an integer into a floating point.
In [4]: 1/5
Out[4]: 0
In [5]: math.ceil(1/5)
Out[5]: 0.0
In [7]: float(1)/5
Out[7]: 0.2
In [8]: math.ceil(float(1)/5)
Out[8]: 1.0
You could make a round up function for integers like this
>>> def round_up(p, q):
... d, r = divmod(p, q)
... if r != 0:
... d += 1
... return d
...
>>> round_up(1, 5)
1
>>> round_up(0, 5)
0
>>> round_up(5, 5)
1
>>> round_up(6, 5)
2
>>>
Your example doesn't work because an integer dividing an integer is an integer.
As for your min question - what you wrote is probably the best you can do.
I don't know about anything in the standard library, but if you are just trying to make sure the answer is never less than 1, the function is pretty easy:
def min_dev(x,y):
ans = x/y
if ans < 1: # ensures answer cannot be 0
return 1
else: # answers greater than 1 are returned normally
return ans
If, instead, you are looking to round up every answer:
def round_up(x,y):
ans = x//y # // is the floor division operator
if x % y == 1: # tests for remainder (returns 0 for no, 1 for yes)
ans += 1 # same as ans = ans + 1
return ans
else:
return ans
This will round up any answer with a remainder.
I believe Python 3.3 (and I know 3.4) return a float by default for integer division: https://docs.python.org/3/tutorial/introduction.html
Related
This question already has answers here:
Why are these numbers not equal?
(6 answers)
Closed 1 year ago.
this is the code.
import math
a = math.pow(10,100)
b = 10 ** 100
c = 10 ** 100
print(a==b) # false
print(a-b==0) # true
I know the math.pow is not correct while the number is too large. but how to understand the next point that a == b is not the same as a-b == 0 ?
my python version is 3.9.6 64bit
This is because of floatingpoint error that can happen to large or small float number. See more info on https://docs.python.org/3/tutorial/floatingpoint.html
Float numbers is stored as an 53 bit. So this problem will not happen to float numbers lower than 4503599627370496. See https://en.wikipedia.org/wiki/IEEE_754-1985 for more info.
import math
a = math.pow(10,100)
b = 10 ** 100
print(type(a)) # float
print(type(b)) # int
We can see that a is an float and b is an int.
print(int(a)) # 10000000000000000159028911097599180468360808563945281389781327557747838772170381060813469985856815104
If we convert a into an int we will see that the number has changed and is no longer math.pow(10,100)
print(a==b) # false
print(int(a)==int(b)) # false
print(float(a)==float(b)) # true
print(a-b==0) # true
If we try to convert both to int it will be the same as a==b but if we convert both to float it will work. That is because both numbers will get the same conversion error.
When we do print(a-b==0) this will be converted correctly.
math.pow, value type is float
a = math.pow(10,100)
b = float(10 ** 100)
a==b is true
For large numbers, the precision is low that is why one is True, the other is False, if you try with a smaller number, you will see that both will evaluate to be True:
>>> math.pow(10,15)
1000000000000000.0
>>> 10**15
1000000000000000
>>> math.pow(10,15)==10**15
True
>>> math.pow(10,20)
1e+20
>>> 10**20
100000000000000000000
>>> math.pow(10,20) == 10**20
True
But if you look at some larger numbers represented by exponent:
>>> math.pow(10,50)
1e+50
>>>10**50
100000000000000000000000000000000000000000000000000
>>> math.pow(10,50)==10**50
False
If you try to convert it to integer, you'll see that the number just changes:
>>> int(math.pow(10,50))
100000000000000007629769841091887003294964970946560
For larger numbers (like you've used math.pow(10, 100)), a-b == 0 returns False because of Floating point arithmetic.
math.pow() - Converts its arguments to float type
From the Docs:
Unlike the built-in ** operator, math.pow() converts both its arguments to type float.
** and pow() - Returns an Integer.
Use ** or the built-in pow() function for computing exact integer powers.
import math
a = 10**2
b = math.pow(10,2)
c = pow(10,2)
print(f'a: {a}\nb: {b}\nc: {c}')
print(a==b)
print(a-b==0)
a: 100
b: 100.0
c: 100
True
True
From above results, you can see what types they return.
Also a-b == 0 returns True in this case since the numbers are small.
In python, I need to get the rounded down logarithm of positive integers for base 2, including big numbers.
However, since floating point math is used, I might get bad results, for example:
>>> import math
>>> int(math.log(281474976710655, 2))
48
However:
>>> 2 ** 48
281474976710656
So the correct result, rounded down, should be 47.
How can I get the correct value?
In Python 3, integers have a .bit_length method, so you should use that to get your rounded down base 2 logarithm.
Here's a short demo:
m = 2 ** 1000
for n in (281474976710655, m-1, m, m+1):
a = n.bit_length() - 1
b = 2 ** a
print(a, b <= n < 2 * b)
output
47 True
999 True
1000 True
1000 True
In python 3 ints even have an efficient .bit_length() method!
>>> (281474976710655).bit_length()
48
>>> (281474976710656).bit_length()
49
In python 2, instead of using floating point math, count the number of bits:
def log2(n):
assert n >= 1
return len(bin(n)) - 3 # bin() returns a string starting with '0b'
(Edited following this comment)
Could someone help check why the result is always one and let me know what I did wrong? Thanks
Correct result should be: 1/1 + 1/2 + 1/3 == 1.83333333333.
x = int(input("Enter n: "))
assert x > 0, "n must be greater than zero!"
def one_over_n(x):
result = 0
for n in range(x):
n += 1
result += 1 / n
return result
r = one_over_n(x)
print("one_over_n( {0:d} ): {1:f}" .format(x, r))
It will work correctly on python 3, but not in python 2
>>> 1/2
0
That means you are just adding zeroes, to one. You will need to change either numerator or denominator to a float number e.g. 1/2.0, so change your code to
result += 1.0 / n
See Pep 238 to see why it was changed in python 3.
btw floating point numbers can't represent all fractions, so if you are just adding fractions, you can use Fraction class e.g.
>>> from fractions import Fraction as F
>>> F(1,1) + F(1,2) + F(1,3)
Fraction(11, 6)
As an alternative, to force Python 2 perform division as you expect (rather than integer division), add:
from __future__ import division
In Python I would like to divide two numbers and if the answer is not an integer I want the number to be rounded up to the number above.
For example 100/30 not to give 33.3 but to give 4.
Can anyone suggest how to do this? Thanks.
You can use the math.ceil() function:
>>> import math
>>> math.ceil(100/33)
4
you can use the ceil function in math library that python has, but also you can take a look why in a logical sense
a = int(100/3) # this will round down to 3
b = 100/3 # b = 33.333333333333336, a and b are not equal
so we can generalize into the following
def ceil(a, b):
if (b == 0):
raise Exception("Division By Zero Error!!") # throw an division by zero error
if int(a/b) != a/b:
return int(a/b) + 1
return int(a/b)
1/2
gives
0
as it should. However,
-1/2
gives
-1
, but I want it to round towards 0 (i.e. I want -1/2 to be 0), regardless of whether it's positive or negative. What is the best way to do that?
Do floating point division then convert to an int. No extra modules needed.
Python 3:
>>> int(-1 / 2)
0
>>> int(-3 / 2)
-1
>>> int(1 / 2)
0
>>> int(3 / 2)
1
Python 2:
>>> int(float(-1) / 2)
0
>>> int(float(-3) / 2)
-1
>>> int(float(1) / 2)
0
>>> int(float(3) / 2)
1
Python's default division of integers is return the floor (towards negative infinity) with no ability to change that. You can read the BDFL's reason why.
To do 'round up' division, you would use:
>>> a=1
>>> b=2
>>> (a+(-a%b))//b
1
>>> a,b=-1,2
>>> (a+(-a%b))//b
0
To do truncation towards zero, and maintain integer division, you use (a+(-a%b))//b if either a or b are negative and the default division if both are positive.
This will do integer division and always round towards zero:
>>> a=1
>>> b=2
>>> a//b if a*b>0 else (a+(-a%b))//b
0
>>> a=-1
>>> b=2
>>> a//b if a*b>0 else (a+(-a%b))//b
0
>>> a,b=-3,2
>>> a//b if a*b>0 else (a+(-a%b))//b
-1
>>> a,b=3,2
>>> a//b if a*b>0 else (a+(-a%b))//b
1
footnote
Interestingly enough, C99 declares that round towards zero is the default:
#include <stdio.h>
int main(int argc, const char * argv[])
{
int a=-3;
int b=2;
printf("a=%d, b=%d, a/b=%d\n",a,b,a/b);
a=3;
printf("a=%d, b=%d, a/b=%d\n",a,b,a/b);
return 0;
}
Prints:
a=-3, b=2, a/b=-1
a=3, b=2, a/b=1
For what it's worth, my own favourite solution is this one. Integer arithmetic only, a single division, and everything else linear time:
def integer_divide_towards_zero(a, b):
return -(-a // b) if a < 0 else a // b
That assumes that b is positive, but in most of the applications I've seen that's true. If you need to deal with negative b too, then the function becomes marginally more complicated:
def integer_divide_towards_zero(a, b):
return -(-a // b) if (a < 0) ^ (b < 0) else a // b
Some sample outputs:
>>> integer_divide_towards_zero(11, 3)
3
>>> integer_divide_towards_zero(-11, 3)
-3
>>> integer_divide_towards_zero(6, 3)
2
>>> integer_divide_towards_zero(-6, 3)
-2
>>> integer_divide_towards_zero(11, -3)
-3
>>> integer_divide_towards_zero(-11, -3)
3
why reinvent the wheel, when there's a perfectly good math.trunc() function?
import math
print(math.trunc(-3.5))
>>-3
print(math.trunc(3.5))
>>3
Try this. Only works for numbers greater than -1
import math
x = .5
y = -.5
print math.floor(math.fabs(x))
>> 0
print math.floor(math.fabs(y))
>> 0
Correct code to do this is, in my opinion, too obscure to write as a 1-liner. So I'd put it in a function, like:
def int0div(a, b):
q = a // b
if q < 0 and b*q != a:
q += 1
return q
Good features: it works for any size of int, doesn't make any adjustment to the raw (a//b) result unless necessary, only does one division (% also does a division under the covers), and doesn't create any integers larger than the inputs. Those may or may not matter in your application; they become more important (for speed) if you use "big" integers.
Throwing my hat in with a few alternate ideas:
Multiple the sign of the number [abs(x)/x] by the abs(x)/2
(abs(x)/x)*(abs(x)/2)
Perform the addition, but if the number is less than zero add one to shift it closer to 0.
x/2 + int(x<0)
You can also use the Decimal module as part of the standard python libraries.
Specifically,
" The integer division operator // behaves analogously, returning the integer part of the true quotient (truncating towards zero) rather than its floor, so as to preserve the usual identity x == (x // y) * y + x % y:"
>>> -7 // 4
-2
>>> Decimal(-7) // Decimal(4)
Decimal('-1')
Also, have a look at Rounding Modes as they've got quite a few ways to view/round your information - Ceiling, down, floor, half-down, half-even, half-up, up and 05up rounding.
Decimal was written as a solution to the traditional problem of binary mathematics in a world expecting decimals solutions