因此,对于我正在进行的线类,我不断收到错误消息
AttributeError: Line instance has no attribute 'point0'
我正在声明这样的界限:
def __init__(self, point0, point1):
self.x = point0
self.y = point1
def __str__(self):
return '%d %d' % (int(round(self.point0)), int(round(self.point1)))
我得到了我的点类中的x和y,它应该已经是浮点值所以我不需要在我的init方法中检查错误但是我确实检查了我的旋转中是否有point0和point1是浮点数方法:
def rotate(self, a):
if not isinstance(a, float) or not isinstance(self.point0, float) or not isinstance(self.point1, float):
raise Error("Parameter \"a\" illegal.")
self.point0 = math.cos(a) * self.point0 - math.sin(a) * self.point1
self.point1 = math.sin(a) * self.point0 + math.cos(a) * self.point1
那么为什么python一直说它没有属性point0?我还尝试将 init 方法更改为:
def __init__(self, point0, point1):
self.point0 = point0
self.point1 = point1
但是当我这样做时,错误说point0没有属性float。那么为什么我一直收到这个错误?这是我用来测试的代码:
p0 = Point(0.0, 1.0)
p1 = Point(2.0, 3.0)
line = Line(p0,p1)
print line
答案 0 :(得分:1)
我好奇......你对Python的范围了解多少?
在你的班级中,你有一个名为x的成员变量和另一个名为y的变量。您的 init 函数接受一个名为point0的参数,另一个名为point1。它将point0保存在x成员变量中,而point1保存在y中。然后,在您的旋转函数中,您尝试访问名为point0的变量。你看到了问题吗?
编程时要理解的重要事项(在大多数编程语言中都是如此,如果不是全部的话),参数的名称不会影响其他地方的数据名称。我可以将一个名为foo的变量传递给一个带有名为bar的参数的函数。在该函数中,我必须将数据称为bar,因为它是变量的名称。之后,在我调用该函数之后,变量的名称仍然是foo,因为只有函数内部的变量才被称为bar。那有意义吗?
答案 1 :(得分:1)
当你调用它时,你的类接受point0和point1参数。如果您想获取这些参数的值,请使用self.x(for point0)
和self.y(for point1)
或另一种方式;
class Line:
def __init__(self, point0, point1):
self.point0 = point0
self.point1 = point1
我建议你阅读;
Python __init__ and self what do they do?
https://www.ibiblio.org/swaroopch/byteofpython/read/class-init.html
答案 2 :(得分:0)
我将在这里添加另一个答案,因为我缺乏评论其他答案的声誉,因为我觉得这个答案与我以前的答案无关(它解决了与你现在看到的不同的问题) )。
因此。也就是说,看看这行代码:
return '%d %d' % (int(round(self.point0)), int(round(self.point1)))
round是一个带数字参数的函数。但是,self.point0和self.point1不是数字。他们是积分。如果你想要它们的数字,你必须明确地引用它们(即self.point0.x)。
答案 3 :(得分:0)
在显示更正的代码之前的几个要点。 (注意实际上没有太多变化):
不要费心检查参数类型。假设Python程序员负责阅读文档并传递正确值的值。
您的Line
课程正在复制您已在Point
课程中定义的代码。行的属性是Point
个实例,因此您可以使用您定义的方法来实现Line
方法。
显示它们时没有理由将点坐标舍入为整数;显示定义点的实际浮点值。您的Line.__str__
方法可以利用您已定义Point.__str__
的事实。
现在,你的代码更短,更正,并附有一些散布的评论。
import math
class Point:
def __init__(self, x, y):
'''x and y should be floats'''
self.x = x
self.y = y
def rotate(self, a):
'''Rotate the point around the origin by a radians'''
self.x = math.cos(a) * self.x - math.sin(a) * self.y
self.y = math.sin(a) * self.x + math.cos(a) * self.y
# If you *were* going to check if a is a float, you
# need to do it *before* you use it.
def scale(self, f):
'''Scale the point by f units''' # you get the idea
self.x = f * self.x
self.y = f * self.y
def translate(self, delta_x, delta_y):
self.x = self.x + delta_x
self.y = self.y + delta_y
def __str__(self):
# If you're storing floats, it's probably useful
# to output them.
return '(%f, %f)' % (self.x, self.y)
# Operations on a line all involve applying the same operations
# to each of its end points.
class Line:
def __init__(self, point0, point1):
self.point0 = point0
self.point1 = point1
def rotate(self, a):
self.point0.rotate(a)
self.point1.rotate(a)
def scale(self, factor):
self.point0.scale(factor)
self.point1.scale(factor)
# If for whatever reason you didn't want to use Point.scale
# here, the code would be...
# self.point0.x = f * self.point0.x
# self.point0.y = f * self.point0.y
# self.point1.x = f * self.point0.x
# self.point1.y = f * self.point0.y
def translate(self, delta_x, delta_y):
self.point0.translate(delta_x, delta_y)
self.point1.translate(delta_x, delta_y)
def __str__(self):
# You've already defined out to turn a Point into
# a string, so you can take advantage of that here.
return "%s -- %s" % (self.point0, self.point1)