我正在尝试构建一个函数,以对波长到频率转换程序进行内部度量转换,并且一直很难使其正常工作。它非常慢,不会为输出分配正确的标签。如果任何人都可以用另一种方法来解决这个问题,或者是为什么发生这种情况的原因,而我所做的任何修复都可以做到!
def convert_SI_l(n):
if n in range( int(1e-12),int(9e-11)):
return n/0.000000000001, 'pm'
else:
if n in range(int(1e-10),int(9e-8)):
return n/0.000000001 , 'nm'
else:
if n in range(int(1e-7),int(9e-5)):
return n/0.000001, 'um'
else:
if n in range(int(1e-4),int(9e-3)):
return n/0.001, 'mm'
else:
if n in range(int(0.01), int(0.99)):
return n/0.01, 'cm'
else:
if n in range(1,999):
return n/1000, 'm'
else:
if n in range(1000,299792459):
return n/1000, 'km'
else:
return n , 'm'
def convert_SI_f(n):
if n in range( 1,999):
return n, 'Hz'
else:
if n in range(1000,999999):
return n/1000 , 'kHz'
else:
if n in range(int(1e6),999999999):
return n/1e6, 'MHz'
else:
if n in range(int(1e9),int(1e13)):
return n/1e9, 'GHz'
else:
return n, 'Hz'
c=299792458
i=input("Are we starting with a frequency or a wavelength? ( F / L ): ")
#Error statements
if i.lower() == ("f"):
True
else:
if not i.lower() == ("l"):
print ("Error invalid input")
#Cases
if i.lower() == ("f"):
f = float(input("Please input frequency (in Hz): "))
size_l = c/f
print(convert_SI_l(size_l))
if i.lower() == ("l"):
l = float(input("Please input wavelength (in meters): "))
size_f = ( l/c)
print(convert_SI_f(size_f))
答案 0 :(得分:1)
编辑:实际上,range
是一种通常用于创建数字的函数。 因此,当您编写 if n in range(min_value, max_value)
时,此函数会生成所有整数,直到找到匹配项或达到 max_value 。
range
类型代表不变的数字序列,通常用于在for
循环中循环特定次数。
代替写作:
if n in range(int(1e-10),int(9e-8)):
return n/0.000000001 , 'nm'
您应该写:
if 1e-10 <= n < 9e-8:
return n/0.000000001 , 'nm'
还请记住,range
仅适用于整数,而不适用于浮点数。
更多编辑:
对于您的特定用例,您可以定义*(值,符号)对的字典,如下所示:
import collections
symbols = collections.OrderedDict(
[(1e-12, u'p'),
(1e-9, u'n'),
(1e-6, u'μ'),
(1e-3, u'm'),
(1e-2, u'c'),
(1e-1, u'd'),
(1e0, u''),
(1e1, u'da'),
(1e2, u'h'),
(1e3, u'k'),
(1e6, u'M'),
(1e9, u'G'),
(1e12, u'T')])
使用bisect.bisect
函数在该有序集合中查找值的“插入”点。此插入点可用于获取简化值和要使用的SI符号。
例如:
import bisect
def convert_to_si(value):
if value < 0:
value, symbol = convert_to_si(-value)
return -value, symbol
elif value > 0:
orders = list(symbols.keys())
order_index = bisect.bisect(orders, value / 10.0)
order = orders[min(order_index, len(orders) - 1)]
return value / order, symbols[order]
else:
return value, u""
演示:
for value in [1e-12, 3.14e-11, 0, 2, 20, 3e+9]:
print(*convert_to_si(value), sep="")
您得到:
1.0p
0.0314n
0
2.0
2.0da
3.0G
您可以根据需要调整此功能...
答案 1 :(得分:1)
您使用range()
的方式与自然语言中使用的方式相近,以表示实数线的连续段,例如在4.5到5.25范围内。但是range()
在Python中并不意味着那样。这意味着一堆整数。因此,即使浮点值在您指定的范围中,它们也不会出现在range()
函数生成的一堆整数中。
您的第一个测试是
if n in range( int(1e-12),int(9e-11)):
我猜您是这样写的,因为您真正想要的是range(1e-12, 9e-11)
,但您却得到了TypeError: 'float' object cannot be interpreted as an integer
。
但是如果您在解释器提示下执行此操作
>>> range(int(1e-12),int(9e-11))
range(0, 0)
>>> list(range(int(1e-12),int(9e-11)))
[]
您会看到它的含义与您明显期望的完全不同。
测试浮点数是否在给定的范围范围内
if lower-bound <= mynumber <= upper-bound:
答案 2 :(得分:1)
您不需要范围,并且如果基于固定单位大小的固定阈值点将使您的逻辑更加健壮。在给定的比例尺下,这通常是一个单位。
以下是确定所有单位比例的通用方法:
>
每个单位数组必须按从最小到最大的顺序排列。