Schere, Stein, Papier, Echse, Spock

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.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

Zur Schule gehe ich schon seit über 15 Jahren nicht mehr.
Ich habe nach Hilfe gefragt, wusste nicht, dass man dann gleich an den Pranger gestellt wird..
Jankie
User
Beiträge: 592
Registriert: Mittwoch 26. September 2018, 14:06

Hilfe hast du ja bekommen. Der Rest ist aber Eigeninitiative. Wenn du das Tutorial durchgearbeitet hast und dann noch konkrete Fragen hast helfen wir dir.
Sirius3
User
Beiträge: 18265
Registriert: Sonntag 21. Oktober 2012, 17:20

@edebec: um Dir helfen zu können, müssen wir verstehen, wo Du nicht weiter kommst. Mit einer Musterlösung ist Dir ja selbst auch nicht geholfen. Dich will niemand an den Pranger stellen, aber Ehrlichkeit hilft uns, Dir zu helfen.
Hast Du Funktionen verstanden? Wenn ja, dann verwundert die Frage, wie denn nun das Hauptprogramm zu starten ist. Wenn nein, dann fang nochmal bei einfacheren Beispielen an, die erklären, wir man wirkliche Funktionen schreibt (ohne global) und komm dann später zu Deinem Spiel zurück.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@Sirius3

habe es anscheinend nicht verstanden.
Ich habe gelernt, dass man das ganze Programm in Funktionen packt. Diese rufe ich dann in meinem Hauptprogramm am Ende des Codes auf. Ich habe echt viel Mühe in mein Programm gesteckt, deswegen will ich es nicht verwerfen bevor ich es verstanden habe. Nachdem ich noch nicht so tief in der Materie steck und es mir schwer fällt andere Beispiele dann so umzudenken, das es bei mir passen könnte, schien mir der Vergleich von falsch und richtig ein guter Weg zu sein ..

@Jankie
und dafür auch Danke! Dachte mein Lerneffekt wäre erst mal größer wenn ich einen Lösungsvorschlag hatte, so übe ich auch online - falls ich nicht weiter weiß schau ich mir die Lösung an..
Benutzeravatar
sparrow
User
Beiträge: 4535
Registriert: Freitag 17. April 2009, 10:28

@edebec: Dein Programm funktioniert ja grundsätzlich. Es läuft, tut halt nur nicht, wie du erwartest. Also musst du jetzt auf Fehlersuche gehen, warum das so ist und bei der Gelegenheit auch gleich das Wort "global" aus deinem Quelltext entfernen.

Nochmal zu den Funktionen:

Funktionen kapseln Code in (wiederverwendbare) Blöcke.
Jede Funktion bekommt Parameter und gibt ein Ergebnis per return zurück.

Das Beispiel von Jankie

Code: Alles auswählen

def berechne_quadratzahl(zahl):
    return zahl * zahl
    
    
def main():
    eingabe_zahl = int(input("Gib eine Zahl ein: "))
    ergebnis = berechne_quadratzahl(eingabe_zahl)
    print(ergebnis)
    
    
    
main()
berechne_quadratzahl ist der Funktionanme. Das in den Klammern dahinter die Parameter.
return verlässt die Funktion und gibt etwas zurück.

Das Tutorial erklärt Funktionen relativ ausführlich.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@sparrow

Es läuft, tut halt nur nicht, wie du erwartest

Hätte es nicht besser formulieren können...
__deets__
User
Beiträge: 14545
Registriert: Mittwoch 14. Oktober 2015, 14:29

“echt viel Mühe”.

https://stackoverflow.com/questions/359 ... eback-erro

Denkst du wir sind mit dem Klammerbeutel gepudert?

Ein Nachtrag: wenn man aus dem Internet abpinnt, sollte man das auch allumfassend machen. Und nicht entscheidende Teile weglassen.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

Hallo zusammen!

Habe es jetzt überarbeitet, danke @all..

Habe jetzt nur noch ein Problem, meine def score() Funktion gibt keinen Punktestand aus. Kann mir da nochmal jemand weiterhelfen an welcher Stelle es hakt?

Code: Alles auswählen

#Schere Stein Papier Echse Spock

import random

print("Hallo und herzlich Willkommen zu Schere, Stein, Papier, Echse, Spock")
print("zu den Regeln:\nSchere schneidet Papier\nPapier bedeckt Stein\nStein zerquetscht Echse\nEchse vergiftet Spock\nSpock zertrümmert Schere\nSchere köpft Echse\nEchse frisst Papier\nPapier widerlegt Spock\nSpock verdampft Stein\nStein schleift Schere")

RULES = {"Schere":["Papier", "Echse"],
         "Stein":["Schere", "Echse"],
         "Papier":["Stein", "Spock"],
         "Echse":["Papier", "Spock"],
         "Spock":["Stein", "Schere"]}

def check_results(player_choice, computer_choice):
    if player_choice != computer_choice:
        if computer_choice in RULES[player_choice]:
            result = "Du hast gewonnen!"
        else:
            result = "Du hast verloren!"
    else:
        result = "Unentschieden!"
    return result


def main():
    while True:
        play_again() # 
        #print("Lass uns eine Runde spielen!")
        try:
            computer_choice = random.choice(list(RULES.keys()))
            player_choice = input("Bitte wähle eine Spielfigur aus: ")
            print("Computer wählt: ", computer_choice)
            winner = check_results(player_choice, computer_choice)
            print(winner)
        except Exception: # 
            pass
            print("Falsche Eingabe! Versuch es noch ein mal: Bitte wähle aus Schere, Stein, Papier, Echse, Spock!")



def score(player_score, computer_score):
    if player_choice != computer_choice:
        player_score += 1
    else:
        computer_score += 1
    return player_score, computer_score
    print("Player: ", player_score)
    print("Computer: ", computer_score)


def play_again():
    antwort = input("Willst du eine Runde spielen? Ja oder Nein?: ")
    if antwort == "Ja":
        return antwort
    else:
        print("Danke, dass du mein Spiel gespielt hast.")
        score()

#Hauptprogramm
main()
score(0, 0)
Jankie
User
Beiträge: 592
Registriert: Mittwoch 26. September 2018, 14:06

Nach einem return wird die Funktion verlassen. Also muss das print vor das return.

Du hast auch noch ein Fehler bei der Bezeichnung der Variablen in deiner score Funktion. (computer_score, player_score als Paramter, in der Funktion verwendest du allerdings player_choice, computer_choice.
Zuletzt geändert von Jankie am Dienstag 14. Juli 2020, 09:56, insgesamt 1-mal geändert.
Benutzeravatar
sparrow
User
Beiträge: 4535
Registriert: Freitag 17. April 2009, 10:28

Ich würde sogar so weit gehen zu behaupten, die Funktion wird gar nie betreten, weil der Aufruf falsch ist.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@sparrow
wird sie auch nicht, der Fehler liegt denke ich in der viert letzen Zeile bei score()...auch wenn ich score(player_score, computer_score) schreibe klappt nicht...habe ganz unten (0, 0) übergeben als Anfangswert, was mach ich noch falsch?
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@sparrow
wird sie auch nicht, der Fehler liegt denke ich in der viert letzen Zeile bei score()...auch wenn ich score(player_score, computer_score) schreibe klappt nicht...habe ganz unten (0, 0) übergeben als Anfangswert, was mach ich noch falsch?
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@sparrow
wird sie auch nicht, der Fehler liegt denke ich in der viert letzen Zeile bei score()...auch wenn ich score(player_score, computer_score) schreibe klappt nicht...habe ganz unten (0, 0) übergeben als Anfangswert, was mach ich noch falsch?
Benutzeravatar
sparrow
User
Beiträge: 4535
Registriert: Freitag 17. April 2009, 10:28

Die Fehlermeldung, die du uns vorenthältst, sagt dir doch, was im Code falsch ist:

Code: Alles auswählen

TypeError: score() missing 2 required positional arguments: 'player_score' and 'computer_score'
Der komplette Trace:

Code: Alles auswählen

Traceback (most recent call last):
  File "test.py", line 60, in <module>
    main()
  File "test.py", line 27, in main
    play_again() #
  File "test.py", line 57, in play_again
    score()
TypeError: score() missing 2 required positional arguments: 'player_score' and 'computer_score'
Zuletzt geändert von sparrow am Dienstag 14. Juli 2020, 10:04, insgesamt 1-mal geändert.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@Jankie

Du hast auch noch ein Fehler bei der Bezeichnung der Variablen in deiner score Funktion. (computer_score, player_score als Paramter, in der Funktion verwendest du allerdings player_choice, computer_choice.

kann doch nicht mit den _score Variablen arbeiten, die sind doch nur zum hoch zählen?! wo hoch gezählt wird hängt doch davon ab, wer gewonnen hat...oder bin ich auf dem Holzweg?
Jankie
User
Beiträge: 592
Registriert: Mittwoch 26. September 2018, 14:06

Es ist meiner Meinung nach auch nicht nötig dafür eine Funktion zu schreiben. Ich würde die check_results Funktion so abändern, dass entweder "Player", "Computer" oder "None" zurückgegeben wird. Diese Rückgabe würde ich dann in eine Liste schreiben und diese dann mit count("Player") oder count("Computer") auswerten lassen. Du kannst auch einen einfachen Zähler mit einer if Abfrage in deine main() einbauen. Also if winner == "Computer": computer_score += 1.


verwende keine nackten Exceptions! Und was soll das pass dort deiner Meinung nach machen?


#edit:

Du musst der Funktion den Gewinner, den aktuellen Score vom Spieler und den aktuellen Score vom Computer übergeben. Zurückgegeben wird dann nur wieder der score. Also ca so:

Code: Alles auswählen

import random

RULES = {"Schere":["Papier", "Echse"],
         "Stein":["Schere", "Echse"],
         "Papier":["Stein", "Spock"],
         "Echse":["Papier", "Spock"],
         "Spock":["Stein", "Schere"]}

def check_results(player_choice, computer_choice):
    if player_choice != computer_choice:
        if computer_choice in RULES[player_choice]:
            result = "Player"
        else:
            result = "Computer"
    else:
        result = "Gleichstand!"
    return result

def score(winner, player_score, computer_score):
    if winner == "Computer":
        computer_score += 1
    elif winner == "Player":
        player_score += 1
    return computer_score, player_score

def main():
    player_score = 0
    computer_score = 0
    while True:
        player_choice = input(f"Bitte wähle ein Gegenstand aus [{', '.join(RULES.keys())}]: ")
        computer_choice = random.choice(list(RULES.keys()))
        print(f"Computer wählt {computer_choice}!")
        winner = check_results(player_choice, computer_choice)
        print(f"Gewinner: {winner}!")
        computer_score, player_score = score(winner, player_score, computer_score)
        print(f"Player: {player_score}")
        print(f"Computer: {computer_score}")


        

main()
Zuletzt geändert von Jankie am Dienstag 14. Juli 2020, 10:14, insgesamt 1-mal geändert.
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@sparrow

aus der Fehlermeldung werde ich nicht schlau..was soll den in die () gehören wenn die Variablen an der Stelle falsch sind?

Code: Alles auswählen

def play_again():
    antwort = input("Willst du eine Runde spielen? Ja oder Nein?: ")
    if antwort == "Ja":
        return antwort
    else:
        print("Danke, dass du mein Spiel gespielt hast.")
        score(player_score, computer_score)
        
so stimmt es ja auch nicht...habe der Funktion doch in der letzten Zeile (0, 0) übergeben, Plan war es dass ab hier hochgezählt wird..
edebec
User
Beiträge: 20
Registriert: Donnerstag 9. Juli 2020, 14:36

@Jankie

das mit dem Zähler und der if-Abfrage wäre natürlich auch möglich. Und für mich auch leichter Umsetzbar..würde es aber gern in eine eigene Funktion packen. Ich habe damit Probleme und will deswegen damit üben..
Benutzeravatar
sparrow
User
Beiträge: 4535
Registriert: Freitag 17. April 2009, 10:28

@edebec: Eigentlich ist das Problem ganz einfach: Du hast ein Stück Code aus dem Internet genommen, das du nicht verstehst. Jetzt schraubst du, ohne zu wissen was du tust, daran herum.
Schreib es von Grund auf neu. Ohne Vorlage. Denn im Augenblick fehlt dir völlig da Verständnis was Funktionen sind, wie sie funktionieren, was Argumente und was Rückgabewerte sind und wie man sie verwendet. Aus eigener Erfahrung kann ich dir sagen: Das lernt man nur durch Anwenden. Und fertige Lösungen ansehen ist kein Anwenden.
Jankie
User
Beiträge: 592
Registriert: Mittwoch 26. September 2018, 14:06

Habe meinen Beitrag oben editiert und da mal die Lösung für deine Funktion score mit eingebaut. Ob du daraus was lernen kannst weiß ich allerdings nicht.

Die Funktion braucht ja den aktuellen Stand von jeweils Computer und Player, dann muss die Funktion den aktuellen Gewinner wissen, anhand des aktuellen Gewinners werden dann die scores einfach hochgezählt. Zurückgegeben muss dann nur noch der neue Stand.


Auch die play_again() Funktion ist erstens Falsch und zweitens überflüssig. Du könntest einfach eine Abfrage machen und wenn diese mit "Nein" beantwortet wird verlässt du im main() deine Schleife mit break.
Antworten