ich habe eine Klasse, die folgende Beziehung kapselt:
a + b + c = const.
Alle 3 Grᅵᅵen (a,b,c) lassen sich ᅵber properties manipulieren. Nun habe
ich das Problem, wenn der Benutzer der Klasse a=n setzen will, muss ich
b oder c anpassen (oder natᅵrlich beide, aber das will ich nicht). Nun
ᅵberlege ich, welche Mᅵglichkeiten ich habe, dem Benutzer entscheiden zu
lassen, ob b oder c angepasst wird.
- So weit ich weiᅵ kann man properties keine Argumente ᅵbergeben. Ich
kann also nicht per Property sagen: Setze a, passe b (oder c) an.
- Ich kᅵnnte es nicht ᅵber properties machen, sondern ᅵber eine
Funktion: def set_a(new_a, fixed="b") so dass per default c angepasst wird.
- Ich kᅵnnte der Klasse ein neues Attribut spendieren, welches angibt,
welche Grᅵᅵe verᅵndert werden soll: obj.keep_fixed = "b"
Fallen Euch noch andere Lᅵsungen fᅵr dieses Problem ein bzw. wie geht
ihr damit um?
Grᅵᅵe,
Florian
Am Sun, 11 Oct 2009 13:37:23 +0200 schrieb Florian Lindner:
> Hallo,
>
> ich habe eine Klasse, die folgende Beziehung kapselt:
>
> a + b + c = const.
>
> Alle 3 Gr锟斤拷en (a,b,c) lassen sich 锟絙er properties manipulieren. Nun habe
> ich das Problem, wenn der Benutzer der Klasse a=n setzen will, muss ich
> b oder c anpassen (oder nat锟絩lich beide, aber das will ich nicht). Nun
> 锟絙erlege ich, welche M锟絞lichkeiten ich habe, dem Benutzer entscheiden zu
> lassen, ob b oder c angepasst wird.
So ganz spontan w锟絩de ich das 锟絙er Properties machen. :-)
#!/usr/bin/env python
# -*- coding: utf-8 -*-
class Klasse(object):
def __init__(self, konstant):
self._a = 0
self._b = 0
self._c = 0
self._const = konstant
def set_a(self, a):
self._a = a
def get_a(self):
self._a = self._const - self._b - self._c
return self._a
a = property(get_a, set_a)
def set_b(self, b):
self._b = b
def get_b(self):
self._b = self._const - self._a - self._c
return self._b
b = property(get_b, set_b)
def set_c(self, c):
self._c = c
def get_c(self):
self._c = self._const - self._b - self._a
return self._c
c = property(get_c, set_c)
if __name__ == '__main__':
zehn = Klasse(10)
print 'a=', zehn.a # a= 10
print 'b=', zehn.b # b= 0
print 'c=', zehn.c # c= 0
zehn.b = 3
print 'a=', zehn.a # a= 7
print 'b=', zehn.b # b= 3
print 'c=', zehn.c # c= 0
zehn.b = 2
print 'c=', zehn.c # c= 1
print 'a=', zehn.a # a= 7
> So ganz spontan würde ich das über Properties machen. :-)
Sehr interessante Herangehensweise! Wäre ich nicht drauf gekommen...
Ich dachte beim bloßen Draufgucken, daß die Daten dan ja ziemlich hin-
und herspringen müßten, aber ist sauber!
> def set_a(self, a):
> self._a = a
> def get_a(self):
> self._a = self._const - self._b - self._c
> return self._a
>
> a = property(get_a, set_a)
BTW: property läßt sich, wie ich letztens gesehen hab, auch ganz
praktisch als Decorator einsetzen:
> @property
> def a(self):
> self._a = self._const - self._b - self._c
> return self._a
> @a.setter
> def set_a(self, a):
> self._a = a
@property macht ein Property-Objekt draus, das eine Methode setter hat.
Diese kann wiederum als Decorator eingesetzt werden und liefert das
verwendete Property wieder zurück, nachdem ihm die übergebene Methode
als Setter untergejubelt wurde.
Thomas
> Andreas Bruhn schrieb:
>
>> So ganz spontan würde ich das über Properties machen. :-)
>
> Sehr interessante Herangehensweise! Wäre ich nicht drauf gekommen...
>
> Ich dachte beim bloßen Draufgucken, daß die Daten dan ja ziemlich hin-
> und herspringen müßten, aber ist sauber!
Attribute, deren Wert von der Abfragereihenfolge abhängt?
>>> k = Klasse(10)
>>> k.a, k.b, k.c
(10, 0, 0)
>>> k = Klasse(10)
>>> k.b, k.c, k.a
(10, 0, 0)
>>> k = Klasse(10)
>>> k.c, k.a, k.b
(10, 0, 0)
Ich glaube nicht, dass Du damit glücklich wirst...
Peter
> Attribute, deren Wert von der Abfragereihenfolge abhängt?
[snip]
> Ich glaube nicht, dass Du damit glücklich wirst...
Will ich ja auch nich, der OP will es :-) Aber ich denke, je nach
Anwendungszweck kann es genau das sein.
Der erste abgefragte Wert fängt die Diskrepanz ab, danach paßt die Bilanz.
Thomas
Erst sein Python 2.6. gibt es das a.setter. Die getter-property-variante
schon immer.
Diez
> Peter Otten schrieb:
>
>> Attribute, deren Wert von der Abfragereihenfolge abh�ngt?
>
> [snip]
>
>> Ich glaube nicht, dass Du damit gl�cklich wirst...
>
> Will ich ja auch nich, der OP will es :-) Aber ich denke, je nach
> Anwendungszweck kann es genau das sein.
>
> Der erste abgefragte Wert f�ngt die Diskrepanz ab, danach pa�t die Bilanz.
Genau. In der Set-Methode k�nnte man sich auch noch merken welches
Property gerade gesetzt wurde und in der Get-methode dann eine
Exception werfen wenn das gleiche Property direkt nach dem setzen
abgefragt werden soll.
War ja auch nur der erste spontane Gedanke. Ob es nun das ist was der
OP braucht, kann nur der OP sagen.
K�nnte man auch irgendwie mit einer Methode machen, der man vielleicht
das zu �ndernde Property, den neuen Wert eben dieses Property und das
neu zuberechnende Property �bergibt. Aber da will mir jetzt nichts
einfaches/elegantes einfallen.
Vor Jahren hatte ich auch mal diese Problematik. Noch zu meiner Delphi
(4?) Zeit. Aber damals ist dann doch nichts aus dem Projekt geworden.
Deswegen hier noch die ganz spezielle L�sungsm�glichkeit: erstmal
abwarten ob das Projekt nicht sowieso abstirbt. ;-)
Gr��e,
Andreas