以下代码会引发错误:
Traceback (most recent call last):
File "", line 25, in <module>
sol = anna.main()
File "", line 17, in main
sol = list(map(self.eat, self.mice))
File "", line 12, in eat
calc = np.sqrt((food ** 5))
AttributeError: 'int' object has no attribute 'sqrt'
代码:
import numpy as np
#import time
class anaconda():
def __init__(self):
self.mice = range(10000)
def eat(self, food):
calc = np.sqrt((food ** 5))
return calc
def main(self):
sol = list(map(self.eat, self.mice))
return sol
if __name__ == '__main__':
#start = time.time()
anna = anaconda()
sol = anna.main()
print(len(sol))
#print(time.time() - start)
我相信我犯了一个严重的错误,因为看起来Python将NumPy中的'np'解释为整数,但我没有看到为什么会这样。
答案 0 :(得分:13)
我会尝试为那些已经给出的人添加一个精确的答案。 numpy.sqrt
有一些math.sqrt
没有的限制。
import math
import numpy # version 1.13.3
print(math.sqrt(2 ** 64 - 1))
print(numpy.sqrt(2 ** 64 - 1))
print(math.sqrt(2 ** 64))
print(numpy.sqrt(2 ** 64))
返回(使用Python 3.5):
4294967296.0
4294967296.0
4294967296.0
Traceback (most recent call last):
File "main.py", line 8, in <module>
print(numpy.sqrt(2 ** 64))
AttributeError: 'int' object has no attribute 'sqrt'
实际上,2 ** 64
等于18,446,744,073,709,551,616
,并且根据C数据类型的标准(版本C99),long long unsigned integer
类型至少包含{{1}之间的范围并且包含0
。
发生18,446,744,073,709,551,615
因为AttributeError
,看到它不知道如何处理的类型(转换为C数据类型后),默认调用numpy
方法在对象上(但不存在)。如果我们使用浮点数而不是整数,那么一切都可以使用sqrt
:
numpy
返回:
import numpy # version 1.13.3
print(numpy.sqrt(float(2 ** 64)))
因此,您可以在4294967296.0
替换numpy.sqrt
,而不是在math.sqrt
替换calc = np.sqrt(food ** 5)
。
我希望这个错误现在对你更有意义。
答案 1 :(得分:3)
正如其他人注意到的那样,归结为import numpy as np
print(np.sqrt(7131 ** 5))
print(np.sqrt(7132 ** 5))
# 4294138928.9
Traceback (most recent call last):
File "main.py", line 4, in <module>
print(np.sqrt(7132 ** 5))
AttributeError: 'int' object has no attribute 'sqrt'
有效但for a = first element, b = last element; a != last; a = next a
while ( ( b != first element ) and (a + b > z) )
b = previous elemnet of b
if a + b == z
return true
会返回错误:
def as_json
hash = {}
hash["title"] = calendar_title
#hash["description"] = calendar_description
hash["start"] = start_at.strftime("%Y-%m-%d")
hash["end"] = end_at.strftime("%Y-%m-%d")
hash["url"] = "/admin/appointments/#{id}"
hash["base_amount"] = base_amount
hash["start_at"] = start_at
hash["end_at"] = end_at
hash["tech_id"] = technician_id
hash["asset_id"] = asset_id
hash["customer_name"] = customer.full_name(false)
# hash["customer_id"] = customer_id
hash["id"] = id
# hash["cust_addresses"] = customer.addresses
hash["address"] = address
# client_host = ClientHost::Location.find_by_id(address.client_host_locations_id)
# hash["customer_email"] = customer.email
# hash["customer_wholesale"] = customer.wholesale?
# hash["customer_tax_exempt"] = customer.tax_exempt?
# hash["vehicles"] = self.get_vehicles
end
def get_vehicles
vehicles = []
self.appointment_vehicles.each do |av|
hash = {}
hash["appointment_vehicle"] = av
hash["total_amount"] = av.total_amount
hash["vehicle"] = av.vehicle
hash["package_display_title"] = av.package.display_title
hash["package_amount"] = av.package.amount
hash["upgrades"] = self.get_upgrades(av.upgrades)
vehicles.push(hash)
end
return vehicles
由于np.sqrt
docs没有提及论点的任何界限,我认为这是一个numpy bug。
答案 2 :(得分:2)
您可以使用内置函数math.sqrt替换numpy,如下所示:
import math
class anaconda():
def __init__(self):
self.mice = range(10000)
def eat(self, food):
calc = math.sqrt(food ** 5)
return calc
def main(self):
sol = list(map(self.eat, self.mice))
return sol
if __name__ == '__main__':
anna = anaconda()
sol = anna.main()
print(len(sol))
我认为您的代码问题是您可能已达到限制(不确定为什么会引起混淆错误)因为10000 ** 5是一个非常大的数字。 您可以通过将范围(10000)减小到范围(1000)来检查这一点。您会注意到您的代码运行完全正常:
import numpy as np
class anaconda():
def __init__(self):
self.mice = range(1000)
def eat(self, food):
calc = np.sqrt((food ** 5))
return calc
def main(self):
sol = list(map(self.eat, self.mice))
print sol
return sol
if __name__ == '__main__':
anna = anaconda()
sol = anna.main()
print(len(sol))
只需将范围(10000)缩小到范围(1000)
,就可以完美地运行答案 3 :(得分:1)
实际上,您既不需要numpy
也不需要math
,因为sqrt(x)
is x**0.5
。所以:
sqrt(x**5) = x ** (5/2) = x ** 2.5
这意味着您可以用以下代码替换您的代码:
class anaconda():
def __init__(self):
self.mice = range(10000)
def eat(self, food):
calc = food ** 2.5
return calc
def main(self):
sol = list(map(self.eat, self.mice))
return sol
if __name__ == '__main__':
anna = anaconda()
sol = anna.main()
print(len(sol))
如果你想使用NumPy,你可以享受这样一个事实:你可以像使用标量一样使用数组:
import numpy as np
class anaconda():
def __init__(self):
self.mice = np.arange(10000)
def eat(self, food):
return food ** 2.5
def main(self):
return self.eat(self.mice)
if __name__ == '__main__':
anna = anaconda()
sol = anna.main()
print(len(sol))
删除所有不需要的面向对象的奇怪名称,您的代码变为:
import numpy as np
print(np.arange(10000) ** 2.5)
答案 4 :(得分:0)
这可能不是您的确切情况,但是如果您想取一个大数的平方根并且想要控制结果的精度,请转到math.sqrt()
或{{1} }不会有太大用处,因为您的结果最终将是浮点数,并且对于足够大的输入,这将达到浮点数的限制。
x ** 0.5
特定情况的一种可能性是研究平方根算法的仅整数实现,例如flyingcircus.util.isqrt()
(免责声明:我是flyingcircus
的主要作者)。
或者,对于更通用的解决方案,可以考虑使用gmpy
(或任何其他具有Python绑定的任意精度库)。