Problem mit Tkinter

Fragen zu Tkinter.
Antworten
MrAlmuench
User
Beiträge: 1
Registriert: Freitag 13. November 2015, 10:57

Bei dem folgenden Code kommt bei mir diese:

Code: Alles auswählen

Exception in Tkinter callback
Traceback (most recent call last):
  File "C:\Python34\lib\tkinter\__init__.py", line 1533, in __call__
    return self.func(*args)
  File "//MNSplusFile/muenchalexa$/Eigene Dateien/test.py", line 12, in rechnung
    if schritte >= 0 and e1 >= 0 and e2 >= 0 and e3 >= 0 and e4 >= 0:
TypeError: unorderable types: Entry() >= int()
Fehlermeldung.
Ja ich weiss das ich die variablen noch umbenennen muss aber mein problem ist, dass ich nicht weiss wie ich die eingegebenen Werte in der Rechnung verwenden kann.

Code: Alles auswählen

from tkinter import *
import time

def rechnung():
    e1.get()
    e2.get()
    e3.get()
    e4.get()
    schritte.get()
    i=0
    print("First Name: %s\nLast Name: %s" % (e1.get(), e2.get()))
    if schritte >= 0 and e1 >= 0 and e2 >= 0 and e3 >= 0 and e4 >= 0:
        # While-Schleife zur Berechnung
        while i < schritte:
            g014neu = g_0_14 * 0.93 + g_15_49 * 0.02 - g_0_14 * 0.066
            g1549neu = g_0_14 * 0.066 + g_15_49 * 0.97 - g_15_49 * 0.029
            g5064neu = g_15_49 * 0.029 + g_50_64 * 0.925 - g_50_64 * 0.066
            g65neu = g_50_64 * 0.066 + g_65 * 0.972
            g_0_14 = g014neu
            g_15_49 = g1549neu
            g_50_64 = g5064neu
            g_65 = g65neu
            i += 1
            # Ausgabe, wenn eingegebene Schritte erreicht sind
            if i == schritte:
                text_file = open("Ausgabe.txt", "a")
                with open("Ausgabe.txt", "a") as text_file:
                    print('Die errechneten Populationswerte nach', schritte, 'Schritt(en), am ',
                          time.strftime('%d.%m.%Y'), 'um ', time.strftime('%H:%M:%S'), 'sind:', file=text_file)
                    print('0-14: ', g_0_14, file=text_file)
                    print('15-49: ', g_15_49, file=text_file)
                    print('50-64: ', g_50_64, file=text_file)
                    print('65+: ', g_65, file=text_file)
                    print('', file=text_file)
                print('Die berechneten Populationswerte nach', schritte, 'Schritten sind:')
                print('0-14 Jahre: ', g_0_14)
                print('15-49 Jahre: ', g_15_49)
                print('50-64 Jahre: ', g_50_64)
                print('+65 Jahre: ', g_65)
            # Falls keine positive Zahl eingegeben wurde
    else:
        print('Bitte geben Sie nur positive Zahlen ein!')
    # Ende der Hauptschleife

master = Tk()
Label(master, text="0-14 Jahre: ").grid(row=0)
Label(master, text="15-49 Jahre: ").grid(row=1)
Label(master, text="50-64 Jahre: ").grid(row=2)
Label(master, text="65+ Jahre: ").grid(row=3)
Label(master, text="Schritte: ").grid(row=4)

e1 = Entry(master)
e2 = Entry(master)
e3 = Entry(master)
e4 = Entry(master)
schritte = Entry(master)

e1.grid(row=0, column=1)
e2.grid(row=1, column=1)
e3.grid(row=2, column=1)
e4.grid(row=3, column=1)
schritte.grid(row=4, column=1)

Button(master, text='Quit', command=master.quit).grid(row=5, column=0, sticky=W, pady=4)
Button(master, text='Bestätigen', command=rechnung).grid(row=5, column=1, sticky=W, pady=4)

mainloop()
Im vorraus schonmal Vielen Dank für die Antworten.

MFG
MrAlmuench
Zuletzt geändert von Anonymous am Freitag 13. November 2015, 11:04, insgesamt 1-mal geändert.
Grund: Quelltext in Python-Codebox-Tags gesetzt.
BlackJack

@MrAlmuench: Die ersten fünf Zeilen der ”Funktion” haben keinen Effekt. Du rufst die `get()`-Methode auf den `Entry`-Exemplaren auf, die gibt eine Zeichenkette zurück, aber damit machst Du dann gar nichts, die werden also gleich wieder verworfen. Du musst die Inhalte der Eingabefelder dann schon an Namen binden. Und da Du damit rechnen willst, oder zumindest vergleiche mit *Zahlen* anstellen willst, musst Du die Zeichenketten auch in Zahlen umwandeln bevor Du sie an Namen bindest.

”Funktion” im ersten Satz in Anführungszeichen weil das semantisch keine Funktion ist, aber eine sein sollte. Werte (ausser Konstanten) sollten Funktionen und Methoden als Argumente betreten und als Rückgabewerte verlassen und nicht einfach so magisch aus der Umgebung kommen. Das ist sehr unübersichtlich, fehleranfällig, macht solche ”Funktionen” schwer bis gar nicht testbar, was die Fehlersuche erschwert. Auf Modulebene gehört nur Code der Konstanten, Funktionen, und Klassen definiert. Das Hauptprogramm sollte auch in einer Funktion stehen, die üblicherweise `main()` heisst. Was dann zur Folge hat das man nicht mehr so einfach magisch auf alles mögliche Zugreifen kann sondern saubere Schnittstellen hat wo man deutlich besser sieht wie der Datenfluss im Programm abläuft. Um das sauber hin zu bekommen kommt man bei GUI-Programmierung nicht wirklich um objektorientierte Programmierung herum.

Programmlogik und Benutzerinteraktion sollte man sauber trennen, damit man die Programmlogik leichter testen und wiederverwenden kann. Die Berechnung sollte also nichts von der GUI wissen müssen und auch sonst keine Ein- und Ausgaben tätigen. Man kann da zur Fehlersuche mal ein ``print`` reinwerfen, aber im Produktivcode sollte das dann nicht mehr stehen.

``while`` ist die falsche Schleifenart wenn man die Anzahl der Durchläufe vorher kennt.

Du öffnest die Textdatei für die Ausgabe zweimal und benutzt ein Dateiobjekt nicht und schliesst dieses auch nicht wieder explizit.
__deets__
User
Beiträge: 14541
Registriert: Mittwoch 14. Oktober 2015, 14:29

Schau dir mal die Zeilen vor deinem Fehler an, alle der Form "feld.get()". Die holen die Werte aus dem Texteingabefeld, und machen was damit? Genau. Nichts. Das ist kein magisches Kommando, welches dann fuer den Code danach alles mit dem Namen "feld" durch das ersetzt, was du gerne haettest.

Stattdessen musst du den Wert einer Variablen zuweisen. Das alleine wird aber auch nicht reichen, du musst noch konvertieren zu dem Datentypen, den du wuenschst - ich vermute mal float.

Code: Alles auswählen

v_schritte = float(schritte.get())
Alternativ kannst du auch gleich eine DoubleVar an das Feld binden, das hat den Vorteil, dass du dann verhinderst, falsche Werte einzugeben.
Antworten