[英]How set list value for attribute of class in python
I have created a class distance_neighbor
in which one of the attributes is a list of objects of class Crime
.我创建了一个
distance_neighbor
类,其中一个属性是Crime
类的对象列表。
That is the value for all attributes I get from database query result.这是我从数据库查询结果中获得的所有属性的值。
At first, I have set data_Crime
list as the value for attribute **Crime
on class distance_neighbor
, and I used del to clear data_Crime list after used, so that the data_Crime
list can used in the next loop.首先,我将
data_Crime
list 设置为类distance_neighbor
上属性**Crime
的值,使用后我使用 del 清除 data_Crime list,以便data_Crime
list 可以在下一个循环中使用。
This is my code:这是我的代码:
conn = psycopg2.connect("dbname='Chicago_crime' user='postgres' host='localhost' password='1234'")
cur= conn.cursor()
minDistance=float(input("Nilai minimum distance : "))
cur.execute("""SELECT id_objek1, objek1, id_objek2, objek2, distance from tb_distance1 where distance<'%f'""" %(minDistance))
class Crime:
def __init__(self, id_jenis, jenis):
self.id_jenis=id_jenis
self.jenis=jenis
class distance_neighbor (Crime):
def __init__(self, distance, **Crime):
self.distance = distance
self.Crime = Crime
data_Crime =[]
data_distance = []
for id_objek1, objek1, id_objek2, objek2, distance in cur.fetchall():
data_Crime.append(Crime(id_objek1,objek1))
data_Crime.append(Crime(id_objek2,objek2))
data_distance.append(distance_neighbor(distance, data_Crime))
del data_Crime[:]
error Message:错误信息:
data_distance.append(distance_neighbor(distance, data_Crime))
TypeError: __init__() takes exactly 2 arguments (3 given)
I have fixed my code using below answers guys, Thank you我已经使用以下答案修复了我的代码,谢谢
This should be closer to what you want:这应该更接近你想要的:
class Crime(object):
def __init__(self, id_jenis, jenis):
self.id_jenis=id_jenis
self.jenis=jenis
class DistanceNeighbor(object):
def __init__(self, distance, crimes):
self.distance = distance
self.crimes = crimes
data_distance = []
for id_objek1, objek1, id_objek2, objek2, distance in cur.fetchall():
crimes = [Crime(id_objek1,objek1), Crime(id_objek2,objek2)]
data_distance.append(DistanceNeighbor(distance, crimes))
Classes in Python 2 should always inherit from object
. Python 2 中的类应该总是从
object
继承。 By convention, class names are in CamelCase.按照惯例,类名是驼峰式的。
The inheritance of DistanceNeighbor
from Crime
seems unnecessary.从
Crime
继承DistanceNeighbor
Crime
似乎没有必要。 I changed this.我改变了这个。
Attributes to instance should be lower case, therefore I used crimes
instead of the very confusing reuse of the class name Crime
.属性实例应该是小写,所以我用
crimes
,而不是类名的非常混乱重用Crime
。
This line:这一行:
def __init__(self, distance, **Crime):
takes your list of Crime
instance apart as separate arguments.将您的
Crime
实例列表作为单独的参数分开。 In your case it means the __init__
receives:在您的情况下,这意味着
__init__
接收:
distance, data_Crime[0], data_Crime[0]
this causes this error message:这会导致此错误消息:
TypeError: init() takes exactly 2 arguments (3 given)
The instantiation of Crime
is pretty short. Crime
的实例化很短。 So, instead of the two appends you can create the list of the two Crime
instances in one line:因此,您可以在一行中创建两个
Crime
实例的列表,而不是两个附加:
crimes = [Crime(id_objek1,objek1), Crime(id_objek2,objek2)]
Since this creates a new list in each loop, there is no need to delete the list content in each loop, as you did with del data_Crime[:]
.由于这会在每个循环中创建一个新列表,因此无需像使用
del data_Crime[:]
那样del data_Crime[:]
每个循环中的列表内容。
You've defined your __init__
method in distance_neighbor
as taking arguments (self, distance, **Crime)
.您已在
distance_neighbor
中将__init__
方法定义为接受参数(self, distance, **Crime)
。 The **
before Crime
tells Python to pack up any keyword arguments you're passed into a dictionary named Crime
. Crime
之前的**
告诉 Python 将您传递到的任何关键字参数打包到名为Crime
的字典中。 That's not what you're doing though.这不是你在做什么。 Your call is
distance_neighbor(distance, data_Crime)
where data_Crime
is a list.您的电话是
distance_neighbor(distance, data_Crime)
其中data_Crime
是一个列表。 You should just accept that as a normal argument in the __init__
method:您应该将其作为
__init__
方法中的正常参数接受:
class distance_neighbor (Crime):
def __init__(self, distance, crime):
self.distance = distance
self.crime = crime
This will mostly work, but you'll still have an issue.这通常会起作用,但您仍然会遇到问题。 The problem is that the loop that's creating the
distance_neighbor
objects is reusing the same list for all of them (and using del data_Crime[:]
to clear the values in between).问题是创建
distance_neighbor
对象的循环正在为所有对象重用相同的列表(并使用del data_Crime[:]
清除它们之间的值)。 If you are keeping a reference to the same list in the objects, they'll all end up with references to that same list (which will be empty) at the end of the loop.如果您在对象中保留对同一列表的引用,则它们最终都会在循环结束时引用对同一列表(将为空)的引用。
Instead, you should create a new list for each iteration of your loop:相反,您应该为循环的每次迭代创建一个新列表:
for id_objek1, objek1, id_objek2, objek2, distance in cur.fetchall():
data_Crime = [Crime(id_objek1,objek1), Crime(id_objek2,objek2)]
data_distance.append(distance_neighbor(distance, data_Crime))
This will work, but there are still more things that you probably want to improve in your code.这会起作用,但是您可能还想在代码中改进更多内容。 To start with,
distance_neighbor
is defined as inheriting from Crime
, but that doesn't seem appropiate since it contains instance of Crime
, rather than being one itself.首先,
distance_neighbor
被定义为继承自Crime
,但这似乎并不合适,因为它包含了Crime
实例,而不是它本身。 It should probably inherit from object
(or nothing if you're in Python 3 where object
is the default base).它可能应该从
object
继承(如果您在 Python 3 中,其中object
是默认基础,则不应该继承)。 You may also want to change your class and variable names to match Python convention: CamelCase
for class names and lower_case_with_underscores
for functions, variables and attributes.你也可能要改变你的类名和变量名相匹配的Python约定:
CamelCase
的类名和lower_case_with_underscores
的函数,变量和属性。
def __init__(self, distance, **Crime):
**Crime
is a keyword argument, and expects named arguments. **Crime
是一个关键字参数,需要命名参数。 You don't need that, remove the asterisks.你不需要那个,去掉星号。
Also, rename the argument, it's very confusing that it has the same name as the class:另外,重命名参数,它与类同名非常令人困惑:
class distance_neighbor(Crime):
def __init__(self, distance, c):
self.distance = distance
self.Crime = c
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.