Como você define programaticamente um atributo?


204

Suponha que eu tenha um objeto python xe uma strings , como faço para definir o atributo sem x? Assim:

>>> x = SomeObject()
>>> attr = 'myAttr'
>>> # magic goes here
>>> x.myAttr
'magic'

Qual é a mágica? O objetivo disso, aliás, é armazenar em cache as chamadas parax.__getattr__() .

Respostas:


288
setattr(x, attr, 'magic')

Para obter ajuda:

>>> help(setattr)
Help on built-in function setattr in module __builtin__:

setattr(...)
    setattr(object, name, value)

    Set a named attribute on an object; setattr(x, 'y', v) is equivalent to
    ``x.y = v''.

Editar: No entanto, você deve observar (como indicado em um comentário) que não pode fazer isso em uma instância "pura" de object. Mas é provável que você tenha uma subclasse simples de objeto em que funcione bem. Eu recomendaria fortemente que o OP nunca fizesse instâncias de objetos como esse.


12
Cuidado, no entanto, isso não funciona no seu cenário em que você está criando uma instância de object ().
S.Lott

3
Absolutamente certo, não. Eu convenientemente ignorei isso. Eu recomendaria fortemente que o OP nunca fizesse instâncias de objetos como esse.
1111 Ali Ali Afshar

2
Que pena que não funciona em todos os casos, pois isso seria realmente útil, por exemplo, para adicionar o dirtyatributo à entrada do usuário ...
brice

1
@Brice: setattr funciona em quase todos os casos. Por eficiência e outros motivos, 'objeto' é programado para que você não possa adicionar atributos extras a ele. Você pode fazer isso com sua própria classe com o __slots__atributo
dirkjot

4
Isso também não funciona int. Você pode explicar o porquê? (está em tudo __builtin__?
Jens Timmerman

53

Geralmente, definimos classes para isso.

class XClass( object ):
   def __init__( self ):
       self.myAttr= None

x= XClass()
x.myAttr= 'magic'
x.myAttr

No entanto, você pode, até certo ponto, fazer isso com as funções setattre getattrbuilt-in. No entanto, eles não funcionam objectdiretamente em instâncias .

>>> a= object()
>>> setattr( a, 'hi', 'mom' )
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'object' object has no attribute 'hi'

No entanto, eles trabalham em todos os tipos de classes simples.

class YClass( object ):
    pass

y= YClass()
setattr( y, 'myAttr', 'magic' )
y.myAttr

25
Alguma idéia de por que isso não funciona com instâncias de object ()?
precisa saber é o seguinte

@meawoppl Você deve fazer isso como uma nova pergunta
Tobias KIENZLER

Perguntou aqui .
Jalanb 22/04

1
posso fazer isso com módulos, em vez de classes?
bonobo

21

Seja x um objeto, então você pode fazê-lo de duas maneiras

x.attr_name = s 
setattr(x, 'attr_name', s)
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.