2014-11-07 7 views
21

I mit Attributen einen Python bezweckt a, b, c.Verwendung str.format() Objekt zuzugreifen Attribute

Ich benutze immer noch alte Zeichenfolge Formatierung, also würde ich normalerweise diese manuell drucken:

print 'My object has strings a=%s, b=%s, c=%s' % (obj.a, obj.b, obj.c) 

In letzter Zeit haben meine Saiten wurden super lange erhalten, und ich würde viel lieber der Lage sein, einfach das Objekt übergeben in eine String-Format-Funktion, etwas wie:

print 'My object has strings a=%a, b=%b, c=%c'.format(obj) 

Die Syntax ist jedoch falsch. Ist das möglich?

Antwort

40

können Sie die .attribute_name Notation innerhalb das Format selbst Felder:

print 'My object has strings a={0.a}, b={0.b}, c={0.c}'.format(obj) 

Nachfolgend finden Sie eine Demonstration:

>>> class Test(object): 
...  def __init__(self, a, b, c): 
...   self.a = a 
...   self.b = b 
...   self.c = c 
... 
>>> obj = Test(1, 2, 3) 
>>> 'My object has strings a={0.a}, b={0.b}, c={0.c}'.format(obj) 
'My object has strings a=1, b=2, c=3' 
>>> 

ist jedoch zu beachten, dass Sie die Formatfelder nummerieren brauchen, wenn dies zu tun. Auch, wie Sie sehen können, die str.format Funktion hat seine Formatfelder bezeichnet mit geschweiften Klammern {...}, nicht das % Zeichen.

Für weitere Informationen, hier ist ein Hinweis auf den Format String Syntax in Python.

+3

Das sieht besser zu mir: 'print 'Mein Objekt hat Strings a = {obj.a}, b = {obj.b}, c = {obj.c}'.Format (obj = obj) ' –

+0

Awesome Jungs, danke. Ist die "0" (z. B. 0.a) bezeichnen den Index des Elements, das an das Format? –

+0

@AdamHughes - Genau. Python beginnt bei "0" zu nummerieren, genau wie C/C++. '0' ist das erste (einzige) Argument zu' str.format'. – iCodez

5

Wie @igniteflow in einem vergrabenen Kommentar schrieb:

'My object has strings a={a}, b={b}, c={c}'.format(**obj.__dict__) 

Mit meinem begrenzten Python Verständnis: .__dict__ ist ein dict mit allen Instanzen-Attributen und der ** Operator im Grunde packt sie aus und fügt sich als Schlüssel = Wert args das Verfahren

+1

Schön! Die Verwendung von "**" ist der Schlüssel. Einschließlich .__ dict__ im Beispiel ist unglücklich, weil es dadurch komplizierter aussieht als es ist. z.B. 'Mein Objekt hat Zeichenfolgen a = {a}, b = {b}'. Format (** {'a': 'hi', 'b': 'Mutter'}) – python1981

1

aus Gründen der Vollständigkeit, aufbauend auf @igniteflow und @Christian, könnten Sie den % String-Format Operator und schreiben verwenden:

'My object has strings a=%(a)s, b=%(b)s, c=%(c)s' % obj.__dict__ 
6

Ich denke, es ist besser, vars() zu verwenden, um auf die Attribute eines Objekts als dict statt usgn __dict__ zuzugreifen.

So könnten Sie dies tun:

"My object has strings a={a}, b={b}, c={c}".format(**vars(obj)) 

Weiteren Hintergrund warum vars()-__dict__ vorzuziehen ist, Use dict or vars()? die Antwort auf die Frage zu sehen.

0

Einige der vorgeschlagenen Antworten, die auf vars(...) verlassen Sie sich nicht mit unveränderlichen Objekten arbeiten:

>>> class foo(object): 
... __slots__ =() 
... def __init__(self): 
...  self.x = 1 
... 
>>> vars(foo()) 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
    File "<stdin>", line 4, in __init__ 
AttributeError: 'foo' object has no attribute 'x' 

Ich denke, es mit etwas zuverlässig und explizit bleiben bevorzugt Liste, was Sie gedruckt werden müssen.

Wenn Sie eine Tonne Attributen diese Werte dann zu drucken, zu speichern als Attribute nicht die beste Idee sein könnte.

Verwandte Themen