Anfängerprojekt IBAN-Tool mit Anfängernachfrage

Stellt hier eure Projekte vor.
Internetseiten, Skripte, und alles andere bzgl. Python.
Antworten
warpy
User
Beiträge: 6
Registriert: Samstag 28. November 2020, 12:32

Hallo zusammen,

ich beschäftige mich seit ein paar Tagen mit Python und lerne nach einem Anfängerkurs autodidaktisch weiter, indem ich mir Dinge ausdenke, die ich programmieren könnte und die nur ein wenig über das hinausgehen, das ich schon kann. Mein aktuelles Projekt ist ein Tool, mit dem man aus BLZ und Kontonummern IBANs ausrechnen kann (und umgekehrt) sowie eine eingegebene IBAN auf Gültigkeit überprüfen kann.

Das Tool funktioniert, ich würde nur gern an einer Stelle (Zeile 24) dafür sorgen, dass die erzeugte IBAN nicht am Stück, sondern in den besser lesbaren Viererblöcken ausgegeben wird. Ich möchte also nach allen vier Zeichen des Strings ein Leerzeichen einfügen und das nicht umständlich über Slicing bewerkstelligen. Ich habe hier im Forum auch schon eine zehn Jahre alte Lösung gefunden (viewtopic.php?t=24474), die in eine Zeile passt. Sie hilft mir aber nicht weiter. Zum einen ist sie nicht erklärt, weil der TO nur eine Erinnerung brauchte, wie das noch einmal ging; zum anderen basiert sie wohl auf Python 2.x und sie wird bei mir entweder im Code überlesen oder wirft einen Fehler aus.

Falls irgendwer Zeit und Lust hat, mir eine aktuelle Lösung zu erklären, damit ich das nächste Mal nicht mehr fragen muss, freue ich mich :D Wenn wem noch anderes Verbesserungspotential an meinem Code auffällt, nehme ich die Ratschläge auch gerne an. Ich könnte mir zum Beispiel vorstellen, dass man das ewige Recasting von String zu Integer und zurück irgendwie umgehen könnte.

Im Voraus vielen Dank für Euer Feedback und Eure Hilfe.
warpy

Code: Alles auswählen

aufgabe=input("""Was wollen Sie tun?
a) iban aus Bankleitzahl und Kontonummer berechnen
b) Bankleitzahl und Kontonummer aus iban berechnen?
c) Eine iban überprüfen
""")
def pruefen():
    global pruefz
    pruefz=str(blz+kto+"131400")
    pruefz=int(pruefz.replace(" ", ""))
    while pruefz>97:
        pruefz=(98-(pruefz%97))
    else:
        pruefz=str(pruefz)
if aufgabe.lower()=="a":
    blz=input(str("""Bitte geben Sie Ihre Bankleitzahl ein.
"""))
    if len(blz)==8:
        kto=input(str("""Bitte geben Sie Ihre Kontonummer ein.
"""))
        kto=str(kto).zfill(10)
        if len(kto)==10:
            pruefen()
            iban=str("DE"+pruefz+blz+kto)
            # Hier fehlt noch eine Funktion, die die IBAN in Viererblöcke aufteilt.
            print("""Die zu Ihren Eingaben passende IBAN lautet:
""", iban)
        else:
            print("Dies ist keine in Deutschland gültige Kontonummer.")
    else:
        print("Dies ist keine in Deutschland gültige Bankleitzahl.")
elif aufgabe.lower()=="b":
    iban=input("""Wie lautet die IBAN, die umgerechnet werden soll?
               """)
    iban=iban.replace(" ", "")
    land=iban[0:2]
    pruef=iban[2:4]
    blz=iban[4:12]
    kto=iban.zfill(10)[12:23]
    pruefen()
    if  len(iban)==22 and land.upper()=="DE" and pruefz==pruef:
        print("Ihre Bankleitzahl lautet: "+blz)
        print("Ihre Kontonummer lautet: "+kto)
    else:
        print("Dies ist keine gültige deutsche IBAN")
elif aufgabe.lower()=="c":
    iban=input("""Wie lautet die IBAN, die geprüft werden soll?
               """)
    iban=iban.replace(" ", "")
    land=iban[0:2]
    pruef=iban[2:4]
    blz=iban[4:12]
    kto=iban.zfill(10)[12:22]
    pruefen()
    if  len(iban)==22 and land.upper()=="DE" and pruefz==pruef:
        print("Dies ist eine gültige deutsche IBAN")
    else:
        print("Dies ist keine gültige deutsche IBAN")  
else:
    print("Bitte geben Sie ab, b oder c ein.")
Benutzeravatar
sparrow
User
Beiträge: 4164
Registriert: Freitag 17. April 2009, 10:28

@warpy:

Zu deinem Code:
Das ist ein fürchterliches Wirrwarr. Ich schreibe mal einfach, was man nicht tut statt direkt auf den Code einzugehen. Am Ende wirst du - wenn du sauberen Code schreiben möchtest - eh von vorne anfangen müssen.

Vergiss, dass es "global" gibt. Wenn dein Programm ohne global nicht funktioniert, dann hast du beim Design etwas grundlegend falsch gemacht.

Funktionen bekommen alles, was sie zum arbeiten brauchen, als Parameter und geben ihr Ergebnis per return zurück. Da musst du noch einmal in die Lektüre gehen.

Such mal nach PEP-8, lies und verstehe es. Das ist die Konvention, wie man Python-Code formatiert.
Insbesondere fressen Leerzeilen vor und nach Funktionen kein Brot - die darf man ruhig setzen.

Verwende aussagekräftige, nicht abgekürzte Variablennamen.

Zeichenketten stückelt man nicht +1 zusammen. Dafür gibt es verschiedene Möglichkeiten Zeichenketten zu formatieren. Insbesondere seit 3.6 die sogenannten f-Strings.

Warum verwendest du Multiline-Zeichnekettenbei den Texten für die Eingabe? Um einen Zeilenumbruch unterzubringen? Das tust du, indem du einen Zeilenumbruch ('\n') in die Zeichenkette einfügst.


Üblicherweise sieht der Einstiegspunkt in ein Python-Prgramm wie folgt aus:

Code: Alles auswählen

def main():
    # Dein Programm hier

if __name__ == "__main__":
    main()
Außer dem stehen uneingerückt (also auf Modulebene) ausschließlich die Import, die Definition von KONSTANTEN, Klassen und funktionen. Ich denke das wars. Wenn bei dir mehr auf Modulebene steht - zum Beispiel Variablen - dann hast du ein Problem mit deinem Design.


Edit: Oh, und was dein eigentliches Problem angeht:
Das ist doch eine schöne Aufgabe das in eine Funktion zu schreiben.
Du übergibst der Funktion eine Zeichenkette und als Integer, die Anzahl der Zeichen in einer Gruppe.
Und zurück bekommst du eine neue Zeichenkette, die die Lücken enthält.
Was du dafür wissen musst: Wie man über eine Zeichenkette iteriert, we man Zeichenketten aus Zeichen erstellt (die .join Methode auf Zeichenketten), was der Modulo-Operator ist und was er tut und wie man über Zeichenketten iteriert.
warpy
User
Beiträge: 6
Registriert: Samstag 28. November 2020, 12:32

Vielen Dank für Dein konstruktives Feedback (auch, wenn es mich natürlich für fünf Minuten ernüchtert hat :wink: ). Zum Glück verdiene ich mein Geld anders, aber trotzdem will ich natürlich vernünftigen Code schreiben.
sparrow hat geschrieben: Samstag 28. November 2020, 13:54 Funktionen bekommen alles, was sie zum arbeiten brauchen, als Parameter und geben ihr Ergebnis per return zurück.
Kannte ich tatsächlich nicht und musste irgendwie das Ergebnis der Funktion nach draußen geben und da schien mir global der einfachste Weg. Habe aber gerade mal ein paar einfache Funktionen mit return erstellt und verstehe soweit, wie der Befehl funktioniert. Die Feinarbeit schaue ich mir dann beim Neuprogrammieren meines kleinen Tools an.
sparrow hat geschrieben: Samstag 28. November 2020, 13:54 Insbesondere fressen Leerzeilen vor und nach Funktionen kein Brot - die darf man ruhig setzen. [...] Verwende aussagekräftige, nicht abgekürzte Variablennamen.
Das sind natürlich die Betriebsblindheiten, wenn man eh als Einziger den eigenen Code liest. Aber, klar, vielleicht schaue ich mir den auch mal mit größerem zeitlichen Abstand an. Dann schadet es nicht, wenn ich ihn immer noch verstehe. PEP-8 habe ich in jedem Falle schon einmal notiert und einen ersten Blick reingeworfen.
sparrow hat geschrieben: Samstag 28. November 2020, 13:54Zeichenketten stückelt man nicht +1 zusammen. Dafür gibt es verschiedene Möglichkeiten Zeichenketten zu formatieren. Insbesondere seit 3.6 die sogenannten f-Strings.
Die habe ich mir gerade eben schon einmal oberflächlich angesehen. Ich denke, ich verstehe, worauf Du hinauswillst.
sparrow hat geschrieben: Samstag 28. November 2020, 13:54Warum verwendest du Multiline-Zeichnekettenbei den Texten für die Eingabe? Um einen Zeilenumbruch unterzubringen? Das tust du, indem du einen Zeilenumbruch ('\n') in die Zeichenkette einfügst.
Genau das war der Grund. Aber ich habe es schon ausprobiert und gesehen, dass Dein Befehl den gleichen Effekt hat (und nebenbei mehr Übersichtlichkeit schafft).
sparrow hat geschrieben: Samstag 28. November 2020, 13:54 Außer dem stehen uneingerückt (also auf Modulebene) ausschließlich die Import, die Definition von KONSTANTEN, Klassen und funktionen. Ich denke das wars. Wenn bei dir mehr auf Modulebene steht - zum Beispiel Variablen - dann hast du ein Problem mit deinem Design.
Da muss ich mich dann erstmal reindenken, weil das sicherlich die größte Umstellung ist. Wobei Umstellung insofern relativ ist, dass ich ja erst ganz am Anfang bin und noch nicht viel Falsches/Umständliches verinnerlicht habe.
sparrow hat geschrieben: Samstag 28. November 2020, 13:54 Was du dafür wissen musst: Wie man über eine Zeichenkette iteriert, we man Zeichenketten aus Zeichen erstellt (die .join Methode auf Zeichenketten), was der Modulo-Operator ist und was er tut und wie man über Zeichenketten iteriert.
Schaue ich mir direkt an. Wenn ich das aber erst hätte tun wollen, bevor ich antworte, hätte die Antwort vermutlich recht lange gedauert.

Insgesamt besten Dank. Auch dafür, dass für mein eigentliches Problem Lösungsansätze anstatt einer Musterlösung angegeben wurden. Damit komme ich sehr gut zurecht. Ich schätze nur, dann musst Du damit leben, dass ich die nächste Iteration des Programms auch wieder hier hochlade.
Benutzeravatar
__blackjack__
User
Beiträge: 13004
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

@warpy: `pruefen()` ist als Name irreführend, denn die Funktion prüft gar nichts, die berechnet aus Bankleitzahl und Kontonummer die beiden Prüffziffern. Wobei die Funktion dann auch schon ein Problem hat wenn das Ergebnis <10 ist, denn dann liefert die Funktion nur *eine* Prüfziffer und nicht beide.

Das ``else`` zum ``while`` in der Funktion ist falsch, weil das da überhaupt keinen Sinn macht.

`str()` wird in dem Programm ein paar mal zu oft angwandt. Bei einer Zeichenkette macht es keinen Sinn die an `str()` zu übergeben, da kommt nur wieder eine Zeichenkette bei heraus.

Statt `lower()` bei jedem Vergleich von `aufgabe` aufzurufen würde man das *einmal* direkt nach dem erhalt der Antwort machen.

Bei ``iban.zfill(10)[12:23]`` macht das `zfill()` keinen Sinn und falls man danach nicht wie im Code die feste Länge der IBAN testen würde, wäre hier die Reihenfolge falsch herum.

In den Zweigen zu b) und c) steht sehr viel fast identischer Code, den sollte man in eine Funktion herausziehen.

Zwischenstand (ungetestet):

Code: Alles auswählen

#!/usr/bin/env python3


def berechne_pruefziffern(bankleitzahl, kontonummer):
    pruefzahl = str(bankleitzahl + kontonummer + "131400")
    pruefzahl = int(pruefzahl.replace(" ", ""))
    while pruefzahl > 97:
        pruefzahl = 98 - (pruefzahl % 97)

    return f"{pruefzahl:02}"


def zerlege_iban(iban):
    iban = iban.replace(" ", "").upper()
    land = iban[0:2]
    pruefziffern = iban[2:4]
    bankleitzahl = iban[4:12]
    kontonummer = iban[12:23]
    if not (
        len(iban) == 22
        and land == "DE"
        and berechne_pruefziffern(bankleitzahl, kontonummer) == pruefziffern
    ):
        raise ValueError("invalid IBAN")

    return (land, pruefziffern, bankleitzahl, kontonummer)


def main():
    aufgabe = input(
        "Was wollen Sie tun?\n"
        "a) iban aus Bankleitzahl und Kontonummer berechnen\n"
        "b) Bankleitzahl und Kontonummer aus iban berechnen\n"
        "c) Eine iban überprüfen\n"
    ).lower()
    if aufgabe == "a":
        bankleitzahl = input("Bitte geben Sie Ihre Bankleitzahl ein.\n")
        if len(bankleitzahl) == 8:
            kontonummer = input(
                "Bitte geben Sie Ihre Kontonummer ein.\n"
            ).zfill(10)
            if len(kontonummer) == 10:
                pruefziffern = berechne_pruefziffern(bankleitzahl, kontonummer)
                iban = f"DE{pruefziffern}{bankleitzahl}{kontonummer}"
                #
                # TODO Hier fehlt noch eine Funktion, die die IBAN in
                #   Viererblöcke aufteilt.
                #
                print(
                    "Die zu Ihren Eingaben passende IBAN lautet:\n",
                    iban,
                )
            else:
                print("Dies ist keine in Deutschland gültige Kontonummer.")
        else:
            print("Dies ist keine in Deutschland gültige Bankleitzahl.")

    elif aufgabe == "b":
        try:
            _, _, bankleitzahl, kontonummer = zerlege_iban(
                input("Wie lautet die IBAN, die umgerechnet werden soll?\n")
            )
        except ValueError:
            print("Dies ist keine gültige deutsche IBAN")
        else:
            print("Ihre Bankleitzahl lautet:", bankleitzahl)
            print("Ihre Kontonummer lautet:", kontonummer)

    elif aufgabe == "c":
        try:
            zerlege_iban(
                input("Wie lautet die IBAN, die geprüft werden soll?\n")
            )
        except ValueError:
            print("Dies ist keine gültige deutsche IBAN")
        else:
            print("Dies ist eine gültige deutsche IBAN")

    else:
        print("Bitte geben Sie ab, b oder c ein.")


if __name__ == "__main__":
    main()
“Most people find the concept of programming obvious, but the doing impossible.” — Alan J. Perlis
warpy
User
Beiträge: 6
Registriert: Samstag 28. November 2020, 12:32

__blackjack__ hat geschrieben: Samstag 28. November 2020, 15:50 @warpy: `pruefen()` ist als Name irreführend, denn die Funktion prüft gar nichts, die berechnet aus Bankleitzahl und Kontonummer die beiden Prüffziffern. Wobei die Funktion dann auch schon ein Problem hat wenn das Ergebnis <10 ist, denn dann liefert die Funktion nur *eine* Prüfziffer und nicht beide.
...
Bei ``iban.zfill(10)[12:23]`` macht das `zfill()` keinen Sinn und falls man danach nicht wie im Code die feste Länge der IBAN testen würde, wäre hier die Reihenfolge falsch herum.
Das sind alles tatsächlich Altlasten, die im Laufe der Zeit von der Entwicklung überholt wurden. Am Anfang wollte ich die komplette IBAN-Prüfung in die Funktion legen, habe dann aber gemerkt, dass ich eigentlich in allen drei "Aufgaben" die Prüfziffer berechnen muss, aber danach andere Prozesse habe. Also fielen die Prozesse danach raus, damit ich die Funktion universell einsetzen kann. Der Name blieb dabei aber unverändert. Ursprünglich stand auch mal ein zfill(2) hinter der ermittelten Prüfziffer. Warum das weggefallen ist, kann ich jetzt gerade nicht sagen. Aber Du hast natürlich Recht, dass da irgendetwas, das die Zweistelligkeit sicherstellt, hingehört. Ähnlich wird es vermutlich bei dem zfill(10) für die Kontonummer gewesen sein: Irgendwann machte das mal Sinn und später störte es den Ablauf des Programms nicht.
__blackjack__ hat geschrieben: Samstag 28. November 2020, 15:50Das ``else`` zum ``while`` in der Funktion ist falsch, weil das da überhaupt keinen Sinn macht.
Ich wollte sichergehen, dass am Ende eine Zahl <97 rauskommt. Aber ja, geht auch ohne, wie ich gerade feststellen konnte.
__blackjack__ hat geschrieben: Samstag 28. November 2020, 15:50`str()` wird in dem Programm ein paar mal zu oft angwandt. Bei einer Zeichenkette macht es keinen Sinn die an `str()` zu übergeben, da kommt nur wieder eine Zeichenkette bei heraus.
Wie gesagt, den Punkt habe ich ja selbst gesehen. Ich muss halt ständig zwischen int und str hin- und herwechseln, weil ich manchmal Operationen mache, die einen String erfordern, während andere einen Integer voraussetzen. Vielleicht kenne ich aber auch einfach nur nicht die entsprechenden Funktionen für den jeweils anderen Typ. In dem Zusammenhang: Wo kommt in dieser Zeile das "f" her und was tut das da (Stichwort zum Selbststudium reicht völlig)? -----return f"{pruefzahl:02}"-----
__blackjack__ hat geschrieben: Samstag 28. November 2020, 15:50In den Zweigen zu b) und c) steht sehr viel fast identischer Code, den sollte man in eine Funktion herausziehen.
Hatte ich tatsächlich mehrfach drüber nachgedacht. Der Hintergedanke, es nicht zu tun, war folgender: wenn ich das in eine Funktion auslagere und an den Anfang des Programms stelle, verlängert das unnötig die Laufzeit für den Fall a), in dem ich die Funktion nicht brauche. Und zwischen Fall a) und Fall b) wollte ich die Funktion der Übersichtlichkeit halber auch nicht stellen. Also habe ich es ohne Funktion gemacht.
Sirius3
User
Beiträge: 17711
Registriert: Sonntag 21. Oktober 2012, 17:20

Das f ist eine Format-String.
Über Laufzeit muß man sich erst Gedanken machen, wenn es wirklich ein Problem ist. Und meist ist das saubere Programm auch von der Laufzeit her besser. Wie hier, wenn der Compiler weniger Code parsen muß, ist er schneller, also das genaue Gegenteil, von dem, was Du da vermutest. Und geparst werden, muß immer das gesamte Programm, weil das ja vor der Ausführung passiert und man so noch gar nicht wissen kann, welcher Zeig tatsächlich betreten wird.
warpy
User
Beiträge: 6
Registriert: Samstag 28. November 2020, 12:32

@Sirius
Danke für den Hinweis. Mir scheint, dass bei mir noch einige Miskonzeptionen bezüglich Python im Besonderen und Programmieren im Allgemeinen bestehen. Unter anderem ging ich davon aus, dass Programm einfach von oben nach unten gelesen wird (bis auf das Zurückspringen bei Funktionen).

@all
Ich habe gerade ein Brett vor dem Kopf. ich habe den Code jetzt ziemlich überarbeitet und finde ihn tatsächlich selbst sehr viel übersichtlicher. PEP-8-konform ist er aber noch nicht. Bevor ich mich daran begebe, will ich das Programm erst einmal zum Laufen kriegen. Und da hapert es noch an der einen oder anderen Stelle:

1. Die Viererblöcke, die meine ursprüngliche Frage waren, klappen noch nicht. Darum konnte ich mich nicht kümmern, weil sie erst einmal in den Hintergrund gedrängt worden sind. Bevor ich mich um diese Kosmetik kümmern kann, muss der Rest laufen. Aufgabe a) läuft ansonsten aber (wieder) komplett.

2. Die Zweistelligkeit der berechneten Prüfziffer klappt jetzt auch nicht mehr mit zfill, weil die Variable an der Stelle als integer vorliegt und zfill damit nicht klappt. Bevor ich einfach blackjacks Lösung kopiere, will ich mir das aber noch einmal genauer ansehen und verstehen.

3. Nachdem ich mir jetzt einen abgebrochen habe, bei den Aufgaben b) und c) die Tupel-Ausgabe der ersten Funktion in die zweite zu bekommen, passiert etwas Merkwürdiges: Obwohl alle Werte korrekt sind, sagt mir die If-Abfrage, dass es sich nicht um eine gültige IBAN handele. Ich habe die (gültige) IBAN DE43123456789012345678 genommen und zur Sicherheit die beiden Ausgaben der Funktionen ausgedruckt. Es stimmt alles mit den Anforderungen der if-Funktion überein. Wo liegt mein Denkfehler?

Code: Alles auswählen

def iban_aufgliedern(iban):
    iban=iban.replace(" ", "")
    land=iban[0:2]
    pruefziffer_eingegeben=iban[2:4]
    bankleitzahl=iban[4:12]
    kontonummer=iban[12:23]
    return (land, pruefziffer_eingegeben, bankleitzahl, kontonummer)


def pruefziffer_ermitteln(bankleitzahl, kontonummer):
    pruefziffer_berechnet=f"{bankleitzahl}{kontonummer}131400"
    pruefziffer_berechnet=int(pruefziffer_berechnet)
    while pruefziffer_berechnet>97:
        pruefziffer_berechnet=98-(pruefziffer_berechnet%97)
        # Hier muss noch die Zweistelligkeit sichergestellt werden
    return pruefziffer_berechnet


def main():
    aufgabe = input("""Was wollen Sie tun?
a) iban aus Bankleitzahl und Kontonummer berechnen
b) Bankleitzahl und Kontonummer aus iban berechnen?
c) Eine iban überprüfen
""").lower()    
        
    if aufgabe == "a":
        bankleitzahl = input(str("Bitte geben Sie Ihre Bankleitzahl ein. \n"))
        if len(bankleitzahl) == 8:
            kontonummer = input(str("Bitte geben Sie Ihre Kontonummer ein. \n"))
            kontonummer = kontonummer.zfill(10)
            if len(kontonummer) == 10:
                pruefziffer_berechnet = pruefziffer_ermitteln(bankleitzahl, kontonummer)
                iban = f"DE{pruefziffer_berechnet}{bankleitzahl}{kontonummer}"
                """Alternativ die vorletzte Zeile streichen und stattdessen in der letzten
                <> iban=f"DE{pruefziffer_ermitteln(bankleitzahl, kontonummer}{bankleitzahl]{kontonummer} </>
                Ich habe aber damit gerechnet, dass die Verschachtelung unübersichtlich erscheint."""
                # Hier fehlt noch eine Funktion, die die IBAN in Viererblöcke aufteilt.  
                print(f"Die zu Ihren Eingaben passende IBAN lautet: {iban}")
            else:
                print("Dies ist keine in Deutschland gültige Kontonummer.")
        else:
            print("Dies ist keine in Deutschland gültige Bankleitzahl.")

    elif aufgabe == "b":
        iban = input("Wie lautet die IBAN, die umgerechnet werden soll? \n")
        iban_aufgliedern(iban)
        land, pruefziffer_eingegeben, bankleitzahl, kontonummer = iban_aufgliedern(iban)
        # print(iban_aufgliedern(iban))
        # print(pruefziffer_ermitteln(bankleitzahl, kontonummer))
        if len(iban) == 22 and land.upper() == "DE" and pruefziffer_ermitteln(bankleitzahl, kontonummer) == pruefziffer_eingegeben:
            print("Ihre Bankleitzahl lautet: {bankleitzahl}")
            print("Ihre Kontonummer lautet: {kontonummer}")
        else:
            print("Dies ist keine gültige deutsche IBAN")
        
    elif aufgabe == "c":
        iban = input("Wie lautet die IBAN, die geprüft werden soll? \n")
        iban_aufgliedern(iban)
        land, pruefziffer_eingegeben, bankleitzahl, kontonummer = iban_aufgliedern(iban)
        if  len(iban) == 22 and land.upper() == "DE" and pruefziffer_ermitteln(bankleitzahl, kontonummer) == pruefziffer_eingegeben:
            print("Dies ist eine gültige deutsche IBAN")
        else:
            print("Dies ist keine gültige deutsche IBAN")
        
    else:
        print("Bitte geben Sie a, b oder c ein.")
        
        
main()
Benutzeravatar
__blackjack__
User
Beiträge: 13004
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

@warpy: `pruefziffer_ermitteln()` liefert eine ganze Zahl und die vergleichst Du mit einer Zeichenkette. Das ist niemals gleich.

Warum rufst Du `iban_aufgliedern()` immer zweimal hintereinander auf? Zumal das Ergebnis vom ersten Aufruf auch überhaupt gar nicht verwendet wird. Also nicht mal an Namen gebunden wird.
“Most people find the concept of programming obvious, but the doing impossible.” — Alan J. Perlis
warpy
User
Beiträge: 6
Registriert: Samstag 28. November 2020, 12:32

__blackjack__ hat geschrieben: Montag 30. November 2020, 00:18 @warpy: `pruefziffer_ermitteln()` liefert eine ganze Zahl und die vergleichst Du mit einer Zeichenkette. Das ist niemals gleich.
Aaaah, natürlich. Habe jetzt in der if-Abfrage umformuliert in

Code: Alles auswählen

and str(pruefziffer_ermitteln(bankleitzahl, kontonummer)) == pruefziffer_eingegeben:
und jetzt hakt es da nicht mehr. Danke.

Was das doppelte iban_aufgliedern() angeht, war das mal wieder ein Relikt, das nicht gelöscht wurde, als ich endlich meine Daten an pruefziffer_ermitteln() übergeben konnte. Da muss ich wohl deutlich besser drauf achten, bis ich irgendwann so fit bin, dass "educated guesses" nicht mehr Teil meiner Methode sind.

Dann widme ich mich mal den anderen Punkten.
Sirius3
User
Beiträge: 17711
Registriert: Sonntag 21. Oktober 2012, 17:20

Jetzt hast Du von den beiden möglichen Varianten genau die falsche genommen.
warpy
User
Beiträge: 6
Registriert: Samstag 28. November 2020, 12:32

Warum? Inwiefern macht das einen Unterschied? Generell oder in diesem besonderen Fall? Wird int immer bevorzugt?

Da ja danach direkt die Ausgabe kommt, scheint mir das gleichgültig, ob ich die eine Variable zu int oder die andere zu str recaste.
Benutzeravatar
__blackjack__
User
Beiträge: 13004
Registriert: Samstag 2. Juni 2018, 10:21
Wohnort: 127.0.0.1
Kontaktdaten:

@warpy: Weil die Funktion ja eigentlich zwei Prüfziffern liefern sollte. Und das tut sie nicht. Statt das an dem Ende zu korrigieren hast Du jetzt die Eingabe dem falschen Format/Typ des Funktionsergebnisses angepasst.

Edit: Okay ich erzähle Unsinn. Und Sirius3 hat IMHO unrecht.

Die Umwandlung in `str` ist richtig, aber an der falschen Stelle und fehlerhaft. Das ist vielleicht der Punkt auf den Sirius3 hinaus wollte. Denn bei Prüfziffern mit einer führenden 0 funktioniert das so nicht. Die Funktion sollte eine zweistellige Prüfzahldarstellung als Zeichenkette liefern.
“Most people find the concept of programming obvious, but the doing impossible.” — Alan J. Perlis
Antworten