len() vs __len__: 类型错误: 'float'对象不能解释为整数



我遇到了一个奇怪的错误,我不认为这是我的代码的问题。

这些是我得到的东西:

  • Boundary:表示域和范围,如[1, 10]具有low属性和high属性,本例中为low = 1high=10
  • Lim:表示并集,这样[1, 10]U[20, 30]存储为self.boundaries = [Boundary([1, 10]), Boundary([20, 30])]

这就是我要做的,

  1. 我在boundary中定义了__len__,这样len(Boundary([1, 10])) #=> 9
class Boundary:
def __len__(self):
return abs(self.high - self.low)
  1. 在Lim对象中,我有self.boundaries,这是一个边界对象列表。在边界定义的__len__,我编码Lim的__len__如下:
class Lim:
def __len__(self):
return sum([len(bd) for bd in self.boundaries])

问题发生的原因如下:

class Boundary:
def __len__(self):
return abs(self.high - self.low)
class Lim:
def __len__(self):
return sum([len(bd) for bd in self.boundaries])
print(len(Lim([1, 10], [20, 30])))
# Traceback (most recent call last):
#   File "boundary.py" in <module>
#     print(len(Lim([1, 10], [20, 30])))
#   File "boundary.py", in __len__
#     return sum([len(bd) for bd in self.boundaries])
#   File "boundary.py", in <listcomp>
#     return sum([len(bd) for bd in self.boundaries])
# TypeError: 'float' object cannot be interpreted as an integer

但是这个组合:

class Boundary:
def __len__(self):
return abs(self.high - self.low)
class Lim:
def __len__(self):
return sum([bd.__len__() for bd in self.boundaries])
print(len(Lim([1, 10], [20, 30])))
# Traceback (most recent call last):
#   File "boundary.py",in <module>
#   print(len(Lim([1, 10], [20, 30])))
# TypeError: 'float' object cannot be interpreted as an integer

然而,代码最终以以下组合执行:

class Boundary:
def __len__(self):
return abs(self.high - self.low)
class Lim:
def __len__(self):
return sum([bd.__len__() for bd in self.boundaries])
print(Lim([1, 10], [20, 30]).__len__())
# 19

为什么将len()更改为__len__()会消除错误?如果你能提供一些帮助,我将非常高兴。

正如评论中指出的那样,len与您的用例不兼容。我不知道你的解决方案需要有多灵活,但我想出了一个最小的工作示例:

from typing import List
def dist(boundary: object, m='euclidean') -> float:
"""Computes a given distance for object-typed boundaries.
"""
return boundary.__dist__(m)
def converge(lim: object) -> float:
"""_Integrates_ the distances over boundaries."""
return lim.__converge__()

class Boundary(object):
low = 0
high = 0

def __init__(self, lo: float, hi: float):
self.low = lo
self.high = hi

def __dist__(self, m: str) -> float:
if m == 'euclidean':
return abs(self.high - self.low)
else:
raise Error(f'Unknown distance {m}')
class Lim(object):
boundaries = []
def __init__(self, boundaries: List[Boundary]):
self.boundaries = boundaries
def __converge__(self) -> float:
return sum([dist(bd) for bd in self.boundaries])
print(converge(Lim([Boundary(1.0, 10.0), Boundary(20.0, 30.0)])))
# expect abs(10-1) + abs(30-20) = 9+10 = 19
(据我所知)那是你想要的。此外,您可以引入基于Boundary类的不同Boundary类。对于基本的Boundary类,您可以引入不同的距离度量,对于Lim类(作为一个基本类),您可以创建不同的收敛方案。虽然这个答案并没有针对你最初的问题提出任何一点(都在评论中),但这是否为你勾勒出了前进的方向?

相关内容

  • 没有找到相关文章

最新更新