Suppose I want to create a set of float numbers starting from 0.1 to 0.00001 as first diving by two and then diving by 5. In other words, I'd like to get the numbers shown below.
0.1
0.05
0.01
0.005
0.001
0.0005
0.0001
0.00005
0.00001
For this small example, I wrote the following code snippet which works fine.
import numpy as np
def format_float(num):
return np.format_float_positional(num, trim='-')
num = 0.1
for j in range(9):
if j ==0:
rate=np.round(num*(0.1),j 1)
print(format_float(num))
elif ( (j 1) % 2) != 0:
num=np.round(num*(0.2),j 1)
print(format_float(num))
else:
num =np.round(num/2,j 1)
print(format_float(num))
My question is if there is a more elegant way to perform this operation given different rules. For instance, suppose I would like to get the number between x
and y
where the rule is to first divide by k
and then divide by l
in order. I believe this should be managable through linspace
, but I could not do it.
CodePudding user response:
In [1]: import numpy as np
In [2]: np.repeat(1 / 10**np.arange(1, 5), 2)[1:] * np.array([1., 5.]*4)[:-1]
Out[2]: array([0.1 , 0.05 , 0.01 , 0.005 , 0.001 , 0.0005, 0.0001])
Generalizing for any "pattern":
def rates(smallest_magnitude, pattern):
n = len(pattern)
pows = np.repeat(1 / 10**np.arange(1, smallest_magnitude), n)[(n-1):]
mults = np.array(pattern * (smallest_magnitude - 1))[:-(n-1)]
return np.round(pows * mults, smallest_magnitude)
Demo:
In [4]: print(*rates(5, [1, 5])) # Your original 'pattern'
0.1 0.05 0.01 0.005 0.001 0.0005 0.0001
In [5]: print(*rates(5, [2, 4, 8]))
0.2 0.04 0.08 0.02 0.004 0.008 0.002 0.0004 0.0008 0.0002
In [6]: print(*rates(5, [3, 5, 7, 9]))
0.3 0.05 0.07 0.09 0.03 0.005 0.007 0.009 0.003 0.0005 0.0007 0.0009 0.0003
CodePudding user response:
This works, but I'm not sure it's any better than your method.
import numpy as np
# Create the powers of ten:
a = 0.1 ** np.arange(1,6)
# Interleave the halves in between:
a = np.concatenate((a,a/2))
# Sort and reverse:
a.sort()
a = a[-1::-1]
print(a)
CodePudding user response:
Two ways:
>>> np.cumprod([.1] 4*[1/2, 1/5])
array([1.e-01, 5.e-02, 1.e-02, 5.e-03, 1.e-03, 5.e-04, 1.e-04, 5.e-05,
1.e-05])
>>> 1 / np.cumprod([10] 4*[2, 5])
array([1.e-01, 5.e-02, 1.e-02, 5.e-03, 1.e-03, 5.e-04, 1.e-04, 5.e-05,
1.e-05])