Spielererfolg berechnen nach Wahrscheinlichkeiten

Hallo,

ich habe hier eine Frage bei der ich weniger ein programmiertechnisches Problem habe, sondern mehr ein logisches. Bisher konnte ich auf keine zufriedenstellende Lösung kommen.

Also, zwei Spieler treten virtuell gegeneinander an.

Variante 1:
Spieler 1 hat eine 85,41% Chance ein Spiel zu gewinnen
Spieler 2 hat eine 78,52% Chance ein Spiel zu gewinnen

Variante 2:
Spieler 1 hat eine 83,24% Chance ein Spiel zu gewinnen
Spieler 2 hat eine 84,59% Chance ein Spiel zu gewinnen

Beide Spieler treten Virtuell solange Gegeneinander an, bis einer 6 Begegnungen gewonnen hat.

Habe schon einige verschiedene Varianten mit Random ausprobiert, aber komme einfach nicht auf eine zufriedenstellenden Lösungsansatz.

Auf Codeschnipsel verzichte ich hier jetzt mal, da ich tatsächlich nichts brauchbares habe. Erhoffe mir hier weniger eine Lösung sondern vielmehr einen Denkanstoss.

Vielen Dank im voraus.

Man könnte das vermutlich durchrechnen, ohne den Sinn zu hinterfragen, aber … wenn zwei Spieler gegeneinander Spielen, dann besagen die Zahlen in „Variante 1“, dass bei 10000 Spielen

  • 8541 mal Spieler 1 gewinnt
  • 7852 mal Spieler 2 gewinnt

Nun. Das ist in der Summe mehr als 10000. Das kann sein, wenn „gewinnen“ so viel heißt wie „nicht verlieren“, und damit z.B. auch „unentschieden“ als „gewinnen (für beide)“ gezählt wird aber … es ist wohl ein Nachfragen wert…

1 „Gefällt mir“

Und dass beide ein Spiel gewinnen können, schließt du wohl aus? Jedenfalls legt das die Aufgabenstellung am ehesten nahe. Gruß

Hallo,

ein Beispiel wäre ein Dartspiel. Ein einzelnes Spiel kennt nur einen Gewinner und kein unentschieden. und wenn einer, wie oben erwähnt, einer sechs Spiele gewonnen hat ist das Match beendet. Da gibt es noch zahlreiche andere Beispiele wie Tischtennis usw. Also ein Unentschieden ist ausgeschlossen.

Mein Problem ist, wie wäre ein Rechenweg das Random entschieden wird, ob der mit 85,41% gewinnt oder der mit 78,52%. Wobei die knapp 7% Vorteil für Spieler 1 natürlich Beachtung finden sollen.

Ich hatte es mal versucht mit ein Random Berechnung von 0.00-100.00, und wenn die Zahl Randomzahl innerhalb von 85,41% bei Spieler 1 und/oder 78,52% bei Spieler 2 liegt bekommt er einen Punkt. Das habe ich solange durch eine Schleife laufen lassen bis einer 1 und der andere 0 hatte. Nach knapp 2 Minuten war er fertig. Also war dieser Lösungsansatz nicht der richtige.

Betrachten wir zunächst nur Konstellation 1:

Spieler 1 gewinnt ein Spiel mit der Wahrscheinlichkeit: 85.41/(85.41+78.52)=0.5210150674068199

und verliert ein Spiel mit der Umkehrwahrscheinlichkeit: 1-85.41/(85.41+78.52)=0.4789849325931801

Spieler 2 gewinnt ein Spiel mit der Wahrscheinlichkeit: 78.52/(85.41+78.52)=0.47898493259318

und verliert ein Spiel mit der Umkehrwahrscheinlichkeit: 1-78.52/(85.41+78.52)=0.52101506740682

So … und nun können wir eine Tabelle aufspannen:

Nach 6 Runden hat Spieler 1 mit einer Wahrscheinlichkeit von
((85.41/(85.41+78.52))^6)*1=0.020003302283522723
6 Spiele gewonnen. (Das Ereignis „Sieg“ trat so oft hintereinander auf.)

Nach 7 Runden hat Spieler 1 mit einer Wahrscheinlichkeit von
((85.41/(85.41+78.52))^6)*2=0.040006604567045446
6 Spiele gewonnen.

Nach 25 Runden hat Spieler 1 mit einer Wahrscheinlichkeit von
((85.41/(85.41+78.52))^6)*25=0.500082557088068 (> 50 %)
6 Spiele gewonnen.

Spieler 2 hat dann mit einer Wahrscheinlichkeit von ca. 30 % 6 Spiele gewonnen:
((78.52/(85.41+78.52))^6)*25=0.3019055667724157.

Das heißt, der ganze Spaß endet am häufigsten nach 25 Spielrunden.


Konstellation 2 geht dazu analog.

Hier war ich ein wenig schreibfaul. Korrektur:

Nach 7 Runden hat Spieler 1 mit einer Wahrscheinlichkeit von
((85.41/(85.41+78.52))^6)*(7-6+1)=0.040006604567045446
6 Spiele gewonnen.

Nach 30 Runden hat Spieler 1 mit einer Wahrscheinlichkeit von
((85.41/(85.41+78.52))^6)*(30-6+1)=0.500082557088068 (> 50 %)
6 Spiele gewonnen.

Also sollte das ganze Spiel nach 30 Spielrunden am häufigsten enden.

Aber ich bin nicht zu 100 % sicher, dass der Rechenweg richtig ist. Im Zweifel solltest du dir das einmal aufmalen und durch Simulation prüfen.

Edit: Sorry, natürlich musste ich mich irgendwo verrechnet haben. Hier ist eine Simulation:

public class MyClass {
    public static void main(String args[]) {
      for (int n=6; n<=35; n++) {
          int ended = 0;
          for (int j=0; j<1000; j++) {
              int win1 = 0;
              int win2 = 0;
              for (int i=0; i<n; i++) {
                  if (Math.random() < 0.52101506740682) {
                      win1++;
                  } else {
                      win2++;
                  }
              }
              if (win1 >= 6) {
                  ended++;
              }
          }
          System.out.println("n: " + n + ", ended: " + (ended / 1000.0));
      }
    }
}

demnach ist es schon nach 10 Spielrunden so weit. Frag mich jetzt aber bitte nicht, wo der Fehler war.

Kleiner Nachtrag: Und alle Spiele sind immer nach minimal 6 und maximal 11 Durchgängen entschieden.

Hallo at-once,

vielen, vielen Dank für deinen Denkanstoss.

Manchmal ist es zu schreien einfach und man kann sich eigentlich nur gegen den Kopf hauen, warum man nicht früher darauf gekommen ist… :crazy_face:

Ich habe ein bisschen mit deiner Simulation herumgespielt und daraus hat sich folgende Methode herauskristallisiert was meinem Anspruch voll und ganz genügt:

Aus

wurde

private void PlayAutomaticGame(TournamentGame match) {
		Random rand = new Random();
		
		// Form: Beiden Spielern wird zu der aktuellen Spielstärke ein zufälliger Wert abgezogen oder hinzugefügt
		double strengthValuePlayer1 = match.getPlayer1().getCurrentstrengthValue() + rand.nextDouble(-5.00,5.00);
		double strengthValuePlayer2 = match.getPlayer2().getCurrentstrengthValue() + rand.nextDouble(-5.00,5.00);
		
		// Wahrscheinlichkeit das Spieler1 ein Spiel gewinnt
		double getwin1 = (avgPlayer1 / (avgPlayer1+avgPlayer2)) * 100;
		
		int score1 = 0;
		int score2 = 0;
		boolean iswin = true;
		while(iswin){
			double legfinish = rand.nextDouble(0.00,100.0);
			if(score1 < 6 && score2 < 6) {
				if(legfinish <= getwin1) {
					score1++;
				} else {
					score2++;
				}
			} else {
				iswin = false;
			}
		}
		System.out.println(" Match Ergebnis: " + score1 + "-" + score2);
	}

Hier das Ergebnis aus einem Testlauf:

Begegnung 1.1: 0.0 Player1 - 84.51 Player2
Match Ergebnis: 0-6

Begegnung 1.2: 80.24 Player3 - 80.55 Player4
Match Ergebnis: 6-3

Begegnung 1.3: 87.37 Player5 - 82.22 Player6
Match Ergebnis: 6-2

Begegnung 1.4: 79.78 Player7 - 81.9 Player8
Match Ergebnis: 4-6

Begegnung 1.5: 81.91 Player9 - 82.05 Player10
Match Ergebnis: 6-2

Im Prinzip genau das was ich wollte. In den meisten Fällen gewinnt der Favorisierte Spieler, aber es sind auch Überraschungen möglich.

Vielen herzlichen Dank nochmal für deinen Hirnschmalz.

Beste Grüße

Meine „Formel“ war aber nicht ganz korrekt. Hier noch einmal richtig:

Unbenannt

Und aus der Liste können dann die Wahrscheinlichkeiten und, dass durchschnittlich nach 11 Spielrunden Schluss ist, abgelesen werden.

Zum Weiterlesen: „Bedingte Wahrscheinlichkeit“ bei Wikipedia …

Gruß

Vielleicht noch die Quelle angeben:

Ich bin mal so frei.

Und hat das etwas mit dem Thema zu tun?

Es ging wohl im die Formel (d.h. diese PNG-Datei). Ich meine ja, bei attributions ziemlich gewissenhaft zu sein, aber … das ist eine Formel. Da wird’s schwer irgendein copyright zu claimen…

Naja, in wissenschaftlichen Arbeiten verifiziere ich anhand der Quelle, ob der benannte Sachverhalt schlüssig ist oder inhaltlich vertrauenswürdig etc.

Der oben genannte Inhalt und vor allem die Formel stammt von einem Forentroll, Daher würde ich den Gehalt dieser Formel noch dem gesagten Von irgendwelchen aus dem Forum ausgeschlossenen Usern trauen.

Mindestens ist es jedoch höchstwahrscheinlich, dass das einfach falsch ist

Wie viele Personen sich hier unterhalten haben, ist nicht ganz klar. Der Anfang sah plausibel aus, aber ich habe nicht jede einzelne Rechnung nachvollzogen. Wer Fehler findet, kann sie gerne korrigieren.