Badminton rules:
1.21 points system, 2 wins in 3 games is better.
2. Scoring system for each ball.
3. In each round, the winning side adds 1 point.
4. When both sides have 20 points, the side leading the other by 2 points wins the game.
5. When both sides have 29 points, the side with the first 30 points wins the match.
6. The winner of one game will serve first in the next game.
The IPO model for this issue is as follows:
Input (I): Ability values of players A and B (expressed as a decimal from 0 to 1), simulate the number of matches
Process (P): Simulate the game
Output (O): Player A and B win the number of matches and probability
To solve this kind of problem, the top-down design is preferred, that is, to start with a total problem, split it into several small problems, consider the solution of each small problem, and finally make the total problem easy to solve. Then you only need to combine the solutions of all the small problems to get a program.
The most important thing in top-down design is the top-level design. Taking sports competition analysis as an example, you can start with the IPO description of the problem. Most programs can simply use the IPO description directly in the program structure design. Sports competition analysis obtains simulation parameters from users to simulate the game, and finally outputs the results.
Step 1: Enter some introduction information
def main(): printinput()
Step 2: Get user input
def main(): printinput() abilityA,abilityB,n=getinput()
Step 3: Use abilityA and abilityB to simulate n games
def main(): printinput() abilityA,abilityB,n=getinput() winsA,winsB=simNGames(n,abilityA,abilityB)
Step 4: Output the result
def main(): printinput() abilityA,abilityB,n=getinput() winsA,winsB=simNGames(n,abilityA,abilityB) printoutcome(winsA,winsB)
From this we divided the total problem into 4 independent functions: printinput (), getinput (), simNGames (), printoutcome ()
Introduction to our input program in the printinput () function
def printinput (): print ( " This program simulates the badminton game of two players A and B " ) print ( " This program requires the ability values of players A and B (expressed as a decimal between 0 and 1) " )
In the getinput () function, we obtain the ability values of players A and B and the number of simulated matches
def getinput(): a = eval (input ( " Please enter the ability value of player A (0-1): " )) b = eval (input ( " Please enter the ability value of player B (0-1): " )) n = eval (input ( " Number of simulation games: " ))
The simNGames () function is the most critical part of the entire program. It can simulate the win-loss relationship of n games and record the number of times the player wins the game
def simNGames(n,abilityA,abilityB): winsA,winsB=0,0 for i in range(n): scoreA,scoreB=simOneGame(abilityA,abilityB) if scoreA>scoreB: winsA+=1 else: winsB+=1 return winsA,winsB
In the simNGames () function, we can see that there is a new function simOneGame (), which is used to simulate the outcome of a game
def simOneGame(abilityA,abilityB): scoreA,scoreB=0,0 Serving = " A " # first right to serve to A the while Not gameOver (scoreA, scoreB, abilityA, abilityB): IF Serving == " A " : IF random () <abilityA: # using random random number A or B is determined to win scoreA + = 1 # A wins plus 1 point else : scoreB + = 1 # B wins plus 1 pointserving = " B " # B wins and will serve the right to B else : if random () < abilityB: scoreB+=1 else: scoreA+=1 serving="B" return scoreA,scoreB
In the simOneGame () function, the gameOver () function is further designed to determine whether a game is over
def gameOver (scoreA, scoreB, abilityA, abilityB): if (scoreA == 21 and scoreB <20) or (scoreA <20 and scoreB == 21 ): return True # 21 points if scoreA == 30 or scoreB == 30 : return True # whoever who wins 30 points IF scoreA == 20 and scoreB == 20: # a and B are 20 minutes case againA, againB = 0,0 Serving = " A " # different simOneGame () function is the same IF Serving == " A " : IF Random () < abilityA: againA+=1 else: againB+=1 serving="B" else: if random()<abilityB: againB+=1 else: againA + = 1 the Serving = " B " return againA == againB + 2 or againB == againA + 2 # who should lead the other two points who won the else : return False
Use the printoutcome () function to print the result of the game
def printoutcome(winsA,winsB): n = winsA + winsB print ( " competition analysis starts, a total of {} games are simulated " .format (n)) print ( " Player A wins {} games, proportion {: 0.1%} " .format (winsA, winsA / n)) print ( " Player B wins {} games, accounting for {: 0.1%} " .format (winsB, winsB / n))
Assemble all the functions, you can get the program to solve the problem:
from random import random def main(): printinput() abilityA,abilityB,n=getinput() winsA,winsB=simNGames(n,abilityA,abilityB) printoutcome(winsA,winsB) def printinput (): print ( " This program simulates the badminton game of two players A and B " ) print ( " This program requires the ability values of players A and B (expressed as a decimal between 0 and 1) " ) def getinput (): a = eval (input ( " Please enter the ability value of player A (0-1): " )) b = eval (input ( " Please enter the ability value of player B (0-1): " )) n = eval (input ( " Number of simulation games: " )) return a, b, n def simNGames (n, abilityA, abilityB): winsA,winsB=0,0 for i in range(n): scoreA,scoreB=simOneGame(abilityA,abilityB) if scoreA>scoreB: winsA+=1 else: winsB+=1 return winsA,winsB def simOneGame(abilityA,abilityB): scoreA,scoreB=0,0 serving="A" while not gameOver(scoreA,scoreB,abilityA,abilityB): if serving=="A": if random()<abilityA: scoreA+=1 else: scoreB+=1 serving="B" else: if random()<abilityB: scoreB+=1 else: scoreA+=1 serving="B" return scoreA,scoreB def gameOver(scoreA,scoreB,abilityA,abilityB): if (scoreA==21 and scoreB<20) or (scoreA<20 and scoreB==21): return True if scoreA==30 or scoreB==30: return True if scoreA==20 and scoreB==20: againA,againB=0,0 serving="A" if serving=="A": if random()<abilityA: againA+=1 else: againB+=1 serving="B" else: if random()<abilityB: againB+=1 else: againA+=1 serving="B" return againA==againB+2 or againB==againA+2 else: return False def printoutcome(winsA,winsB): n = winsA + winsB print ( " competition analysis starts, a total of {} games are simulated " .format (n)) print ( " Player A wins {} games, proportion {: 0.1%} " .format (winsA, winsA / n)) print ( " Player B wins {} games, accounting for {: 0.1%} " .format (winsB, winsB / n)) main()
The results are as follows: