Objekt von einem dictionary für Methoden benutzen

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
swissparadies
User
Beiträge: 1
Registriert: Freitag 11. März 2022, 20:57

Hallo Zusammen

Bei folgendem code kann ich ein Objekt das ich für die Klasse "Savingaccount" erstelle in einem dictionary speichern {Name:Objekt_name} nun wenn ich den objekt_name aus der dictionary nehme und eine methode dazu
benutze z.b Objekt_name.show.credit() erhalte ich einen Fehler: AttributeError: 'str' object has no attribute 'show_credit' Weiss jemand wie ich das beheben könnte?


Hier ist noch der Code mit Menü als erstes bin ich bei 2. um einen Savingaccount zu erstellen dann bei 4. um eine methode auszuführen (Ich würde empfehlen es selber mal zu testen)

Code: Alles auswählen

def print_accounts(accounts):
        print(accounts)
        
        pass
    
    def add_savingaccount(account_name, iban, name, address, accounts): 
        print(accounts, name)
        accounts[name]=account_name
        account_name = SavingAccount(iban , name, address)
        
        
        pass
    
    def get_savingaccount(accounts, name):
        current_account = (accounts.get(name, 'Name nicht verfügbar'))
        print(current_account)
        user_answer = int(input("What do you want to do 1. get credit, 2. withdraw, 3. deposit, 4. close account, 5. open account, 6. change rate, 7. sleep: "))
        
        
        
        
        if user_answer == 1:
            current_account.show_credit()
        
        elif user_answer == 2:
            current_account.withdrawn(int(input("How much do you want to withdraw: ")))
            
        elif user_answer == 3:
            current_account.deposit(int(input("How much do you want to deposit: ")))
            
        elif user_answer == 4:
            current_account.close_account()
            
        elif user_answer == 5:
            current_account.open_account()
            
        elif user_answer == 6:
            current_account.change_interest_rate(int(input("How much do you want to deposit: ")))
            
        elif user_answer == 7:
            current_account.sleep(int(input("Sleep time: ")))
            
        
        pass
    
    
    def load_accounts(accounts, filename):
        with open(filename, "r") as file:
            accounts = json.load(file)
            #for key in phone_book:
            #   accounts[key]=phone_book[key]
            accounts.update(accounts)
        
        pass
    
    def save_accounts(accounts, filename):
    
        with open(filename, "w+") as new_file:
            json.dump(accounts, new_file, separators=(',',':'))
        
        
        pass
    
    def print_menu():
        print ('1. Print Phone Numbers')
        print ('2. Add a SavingAccount')
        print ('4. Get SavingAccount')
        print ('5. Load accounts')
        print ('6. Save accounts')
        print ('7. Quit')
        print()
    
    accounts = {}
    menu_choice = 0
    print_menu()
    
    
    while True:
        menu_choice = int(input("Type in a number (1-7): "))
        if menu_choice == 1:
            print_accounts(accounts)
            print_menu()
    
            
        elif menu_choice == 2:
            print("Add Name and Number (Valid IBAN gets transferred)")
            account_name = input("Accountname: ")
            name = input("Name: ")
            iban = "CH 54 3242 3345 5342 4235"
            address = input("Address: ")
            add_savingaccount(account_name, iban, name, address, accounts)
            print_menu()
    
            
            
        elif menu_choice == 4:
            print("get_savingaccount")
            name = input("Name: ")
            get_savingaccount(accounts, name)
            print_menu()
    
            
        elif menu_choice == 5:
            filename = input("Filename to load: ")
            load_accounts(accounts, filename)
            print_menu()
    
            
        elif menu_choice == 6:
            filename = input("Filename to save: ")
            save_accounts(accounts, filename)
            print_menu()
    
            
        elif menu_choice == 7:
            break
        
        else:
            print_menu()
Benutzeravatar
sparrow
User
Beiträge: 4540
Registriert: Freitag 17. April 2009, 10:28

Warum stehen da so viele pass in deinem Code? Genau keines davon ist nötig.
Warum sind bei dir die Funktionen verschachtelt. Das tut man (außer in wenigen Ausnahmen) nicht. Oder ist das ein Einrückungsfehler? Dann solltest du sorgfältiger prüfen, was du postest. Auch, ob etwas schow.credit oder show_credit heißt.
Wenn die Einrückung hier falsch ist, dann deklarierst du globale Variablen. Schreib dein Programm in eine Funktion "main" und starte die wie folgt:

Code: Alles auswählen

if __name__ == "__main__":
    main()
Das, Importe und die Definition von Konstanten (die so heißen, weil sich der Wert _nie_ ändert), Klassen und Funktionen ist das einzige, was uneingrückt im Code steht.

Grundsätzlich versuchst du show_credit auf einer Zeichenkette aufzurufen. Prüf doch mal, von welchem Typ Objekt_name ist (das sich im Code nirgends findet). Ich denke, das ist nicht was du vermutests. Dein Aufruf von .get() auf das soll ja spätestens dann, wenn der Schlüssel nicht gufunden wird 'Name nicht verfügbar' zurück geben. Und dann crasht dein Programm auf jeden Fall, denn 'Name nicht verfügbar' ist eine Zeichenkette - und Zeichenketten haben keine show_credit() Methode.
Ich sehe aber auch allgemein nicht, wo du etwas anderes als eine Zeichenkette in das dict legst. In add_savingaccount tust du nämlich genau das.
Benutzeravatar
snafu
User
Beiträge: 6873
Registriert: Donnerstag 21. Februar 2008, 17:31
Wohnort: Gelsenkirchen

Du musst halt das neue Objekt ans Dict binden und nicht den String für den Account. Sähe dann so aus:

Code: Alles auswählen

def add_savingaccount(account_name, iban, name, address, accounts): 
    account = SavingAccount(iban , name, address)
    accounts[account_name] = account
Sirius3
User
Beiträge: 18279
Registriert: Sonntag 21. Oktober 2012, 17:20

Du hast hier 120 Zeilen Code geschrieben, aber noch kein einziges Stück davon getestet. So funktioniert Programmieren nicht. Man schreibt eine Funktion und testet die ausführlich, bevor man sich an die nächste macht.
In `add_savingaccount` überschreibst Du den Parameter account_name mit einem SavingAccount-Objekt, machst dann aber nichts mehr damit.
In `get_savingaccount` ist `current_account` im Zweifel ein String, der aber die ganzen Methoden nicht hat, die Du darauf verwenden willst.
In `load_accounts` überschreibst Du wieder einen Parameter `accounts` und machst dann nichts damit.
In `save_accounts´ benutzt Du den Filemode w+ der niemals sinnvoll ist. Das führt nur unter umständen zu kaputten Dateien.
Du rufst in jedem if-Zweig print_menu auf, statt das einmal am Anfang der Schleife zu tun.
Die vielen Leerzeilen machen das Lesen sehr schwierig, weil sie einzelne Funktionen optisch zerreißen.

Überlege Dir zuerst für jede einzelne Deiner Funktionen, was diese Funktion machen soll, welche Parameter sie braucht, und was sie zurückgeben sollte. Dann schreibe ausführliche Tests. Überlege Dir alle möglichen Fälle, die auftreten könnten, auch wie Du auf eventuelle Fehler reagieren willst.
Antworten