简体   繁体   English

随机列表中的对象属性在Python中不可访问

[英]Object Attribute in Random List Not Accessible in Python

I'm working on my first object oriented bit of python and I have the following: 我正在研究我的第一个面向对象的python,我有以下几点:

#!/usr/bin/python 
import random 

class triangle:

# Angle A To Angle C Connects Side F
# Angle C to Angle B Connects Side D
# Angle B to Angle A Connects Side E

    def __init__(self, a, b, c, d, e, f):
        self.a = a
        self.b = b
        self.c = c
        self.d = d
        self.e = e
        self.f = f

    #def solver:
        #pass

#initialize Triangle
myTri = triangle(0,0,0,0,0,0)

#Pick Three Random Angles or Sides to Generate Values For
sample = random.sample([myTri.a, myTri.b, myTri.c, myTri.d, myTri.e, myTri.f],  3)

#Sets the three randomly picked variables to a Random Number



sample[0] = random.randint(1, 100)
sample[1] = random.randint(1, 100)
sample[2] = random.randint(1, 100)

How do I pass myTri.a, for example to random.randint. 我如何将myTri.a传递给random.randint。 It is passing the value of '0' which it initialized. 它正在传递初始化的值“ 0”。 I want to be able to assign a random value to three of the .a-.f attributes of myTri. 我希望能够为myTri的三个.a-.f属性分配一个随机值。 What am I missing? 我想念什么?

When you say [myTri.a, myTri.b, ...] you are not getting a list of the variables themselves, or references to them. 当您说[myTri.a, myTri.b, ...]您没有得到变量本身或对它们的引用的列表。 Instead you are getting just their values. 相反,您只是得到他们的价值观。 Since you know they were initialized to 0 , it is as if you had written [0, 0, 0, 0, 0, 0] . 既然您知道它们已初始化为0 ,就好像您已经编写了[0, 0, 0, 0, 0, 0] There's no difference. 没有区别

Then later when you try to assign to sample[0] , you are actually just overwriting the 0 that is stored in that array with a random value. 然后,稍后当您尝试分配给sample[0] ,实际上只是用一个随机值覆盖了存储在该数组中的0。 Python knows nothing at all about myTri at that point; myTri ,Python对myTri the connection is lost. 连接丢失。

Here's what you can do to get the effect you're aiming for. 您可以按照以下步骤来获得想要的效果。 First, pass a list of variable names we want to assign to later to random.sample : 首先,将稍后要分配给变量的名称列表传递给random.sample

sample = random.sample(["a", "b", "c", "d", "e", "f"], 3)

That'll give us back 3 random variable names. 这将给我们3个随机变量名。 Now we want to assign to the variables with those same names. 现在,我们要为这些变量分配相同的名称。 We can do that by using the special setattr function, which takes an object and a variable name and sets its value. 我们可以通过使用特殊的setattr函数来做到这一点,该函数接受一个对象和一个变量名并设置其值。 For instance, setattr(myTri, "b", 72) does the same thing as myTri.b = 72 . 例如, setattr(myTri, "b", 72)做与myTri.b = 72相同的myTri.b = 72 So rewritten we have: 如此重写,我们有:

setattr(myTri, sample[0], random.randint(1, 100))
setattr(myTri, sample[1], random.randint(1, 100))
setattr(myTri, sample[2], random.randint(1, 100))

The major concept here is that you're doing a bit of reflection, also known as introspection. 这里的主要概念是您在进行反思,也就是自省。 You've got dynamic variable names--you don't know exactly who you're messing with--so you've got to consult with some more exotic, out of the way language constructs. 您已经有了动态变量名-您不知道确切地与谁打交道-因此您必须咨询一些更奇特的语言构造方法。 Normally I'd actually caution against such tomfoolery, but this is a rare instance where introspection is a reasonable solution. 通常,我实际上会警告您不要假装,但这是自省是一种合理解决方案的罕见情况。

To assign to a , b , and c : 分配给abc

myTri.a = random.randint(1, 100)
myTri.b = random.randint(1, 100)
myTri.c = random.randint(1, 100)

To assign to one random attribute from a - f : 分配a - f一个随机属性:

attrs = ['a', 'b', 'c', 'd', 'e', 'f']
setattr(myTri, random.choice(attrs), random.randint(1, 100))

To assign to three random attributes from a - f : 分配a - f三个随机属性:

attrs = ['a', 'b', 'c', 'd', 'e', 'f']
for attr in random.sample(attrs, 3):
  setattr(myTri, attr, random.randint(1, 100))

Alternative to using setattr: do it when you create a Triangle instance. 使用setattr的替代方法:创建Triangle实例时执行此操作。

args = [random.randint(1, 100) for i in xrange(3)] + [0, 0, 0]
random.shuffle(args)
my_tri = Triangle(*args)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM