TreeView - Daten bestimmter Zellen ändern

Fragen zu Tkinter.
Antworten
diablo75
User
Beiträge: 30
Registriert: Dienstag 8. September 2009, 23:12

Hello,

hab wiedermal ein Problem: Ich schaffe es einfach nicht in einem TreeView den Text einer bestimmten Zelle zu ändern.
Wie zu sehen schaffe ich es nur mehrere zu ändern.

Die Daten kommen aus einer Sqlite3 DB und bei Firmen wird bei Anrede der Wert 3 geliefert. Nun will ich diesen Wert von 3 auf Firma ändern. Nur schreibt er mir den String Firma in 5 Zellen mit jeweils 1 Buchstaben und löscht den aktuellen Datensatz.

Liste vorher:
('3', 'XYFirma', ' ', 'Strasse 1', ('Herrn', 'Niklas', 'Johann', 'Kegelg.'), ('Herrn', 'Nikolic', 'Zivanko', 'Wolfgang Schmälzl G.'),

Liste sieht dann so aus:
'Firma', ('Herrn', 'Niklas', 'Johann', 'Kegelg.'), ('Herrn', 'Nikolic', 'Zivanko', 'Wolfgang Schmälzl G.'),
Bild und Code unten :-)

Bild
http://www.edvmax.at/Bilder/python/Treeview.jpg

Code: Alles auswählen

#TreeView mit Daten füllen und einfärben:
    def daten_verarbeiten (self,data):
        global count
        count=0
        data.sort(key= itemgetter(1)) #Sortierung nach 2 Spalte (FamName)

        #Bei Anrede wird bei Firmen eine 3 geliefert - daher 3 in Firma ändern
        #Tuble ist nicht veränderbar daher in list und dann wieder in Tuble umwandeln
        global mylist
        mylist= list(data)

        for x in mylist:
            if x[0] == '3':
                mylist[count] = 'Firma'
                #print(mylist)
            count+=1
                
        mytuple = tuple(mylist)

        
        for record in mytuple:
            if count % 2 == 0:
                self.TreeViewKundenDaten.insert(parent='',index='end',iid=count, text='',values=(record[0], record[1],record[2],record[3]),
                tags=('gerade'))
            else:
                self.TreeViewKundenDaten.insert(parent='',index='end',iid=count, text='',values=(record[0], record[1],record[2],record[3]),
                tags=('ungerade'))                
            count += 1
diablo75
User
Beiträge: 30
Registriert: Dienstag 8. September 2009, 23:12

Habs gelöst - kann geschlossen werden.

Code: Alles auswählen

for x in mylist:
            if x[0] == '3':
                templist = ['Firma',x[1],x[2],x[3]]
                mylist[count] = templist
                #print(mylist)
            count+=1
            
Benutzeravatar
__blackjack__
User
Beiträge: 13068
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

@diablo75: ``global`` hat da nichts zu suchen. Das sollte man sowieso nicht verwenden, aber in einer Methode in einer Klasse ist das richtig falsch.

`count` wird ziemlich weit von der Stelle entfernt definiert an der es dann letztendlich genutzt wird. Dort sollte `enumerate()` verwendet werden. Oder noch besser man verwendet da gar keinen Zähler, sondern baut einfach eine neue Liste auf.

Was auch immer ein ”Tuble” sein mag, Du meinst da ”Tupel” im Kommentar.

Das ist aber auch alles ziemlicher Unsinn. `data` ist bereits eine Liste und kein Tupel, denn sonst hättest Du da `sort()` nicht drauf aufrufen können. Und Du willst ja eigentlich auch gar nicht `data` ändern, sondern Elemente *in* der Liste. *Das* sind Tupel. Die Wandlung der Liste dann in ein Tupel mit Tupeln ist ebenfalls Unsinn. Die Namen für die beiden überflüssigen Zwischenwerte sind mit `mylist` und `mytuple` auch eher schlecht gewählt.

Dein Fehler wird vielleicht deutlicher wenn man sinnvolle Namen verwenden würde. `x` ist kein sinnvoller Name für einen Datensatz. Der Code könnte mit sinnvollen Namen so aussehen:

Code: Alles auswählen

        for index, record in enumerate(data):
            if record[0] == "3":
                data[index] = "Firma"
                # print(data)
Die Schleife liefert den Datensatzindex und den Datensatz. Und falls die erste Spalte im Datensatz den Wert "3" hat, wird der Datansatz am aktuellen Index durch den Text "Firma" ersetzt. Also nicht der erste Wert des Datensatzes wird ersetzt, sondern der gesamte Datensatz wird durch "Firma" ersetzt. Womit klar sein sollte warum dieses Wort auf die Spalten verteilt wird.

Da die Elemente Tupel sind und man Tupel nicht verändern kann, muss man hier für das ersetzen ein neues Tupel erstellen und entweder an den Index setzen, oder aber einfach eine neue Liste mit gegebenfalls veränderten Tupeln aufbauen.

Das `count` in der zweiten Schleife weiterverwendet wird ist komisch, weil so abhängig davon ob `data` eine gerade oder ungerade Anzahl von Datensätzen enthält, es sich ändert ob die Tags "gerade" und "ungerade" am Ende stimmen oder genau gegensätzlich vergeben werden. Und die `iid` startet im Grunde recht willkürlich. Oder zumindest für den Leser unerwartet.

Im ``if``-Zweig steht fast genau das gleiche wie im ``else``-Zweig. Da sollte man weniger Code wiederholen und nur an der einen Stelle unterscheiden, wo sich dann auch tatsächlich etwas unterscheidet.

Die Klammern um den `tags`-Wert sind überflüssig und könnten den Leser leicht irritieren und dazu verleiten zu denken da würde zwingend ein Tupel erwartet.

Die komplette Methode könnte so aussehen (ungetestet):

Code: Alles auswählen

    def daten_verarbeiten(self, data):
        """
        TreeView mit Daten füllen und einfärben.
        """
        data.sort(key=itemgetter(1))  # Sortierung nach 2 Spalte (FamName)
        #
        # Bei Anrede wird bei Firmen eine 3 geliefert - daher 3 in Firma ändern.
        #
        for count, record in enumerate(data):
            self.TreeViewKundenDaten.insert(
                parent="",
                index="end",
                iid=count,
                text="",
                values=(
                    ("Firma", *record[1:4]) if record[0] == "3" else record[:4]
                ),
                tags="gerade" if count % 2 == 0 else "ungerade",
            )
„All religions are the same: religion is basically guilt, with different holidays.” — Cathy Ladman
diablo75
User
Beiträge: 30
Registriert: Dienstag 8. September 2009, 23:12

Danke für die Antwort :-)
Hab das meiste aus Youtube und div. Seiten im Netz.

Muss noch meinen Style in Python anpassen
Antworten