The next example is an experiment on playing Lotto. In this simplified version of Lotto you have to guess seven different numbers in the interval from 1 to 34. You may submit one bet each week. At the end of the week the Lotto system chooses randomly seven different winner numbers, and the winning players are those that have submitted a bet with these winner numbers.
We use a MonitorSystem to represent the players and the Lotto. Lotto is represented by an object with MonitorProcess as superclass. A player is represented by an instance of class Player that is a subclass of MonitorProcess.
The Lotto system has the following overall structure:
LottoExperiment: obj MonitorSystem
mnoOfPlayers: val 500
betSize: val 7
class Hand:
:::
class Bet(thePlayer: ref Player, theHand: ref Hand):
:::
class Player(inx: var integer): MonitorProcess
:::
Lotto: obj MonitorProcess
:::
Lotto.start
generatePlayers: do
...
LottoExperiment has the following main attributes:
- Constants
noOfPlayersandbetSize, which defines the number ofPlayerobjects and the size of aHandin aBet. - Class
Handwhich represents a hand of seven numbers. - Class
Betwhich represents a bet. It has parametersthePlayer, which is thePlayerthat has submitted theBetandtheHand, which is theHandof theBet. - Class
Playerwhich represents a player. - An object
Lotto, which represents the Lotto. - A statement that starts the
Lottoprocess. - An object
generatePlayerswhich is an object that generates the players.
Class Player has the following structure:
class Player: MonitorProcess
cycle
Lotto.submit(Bet(this(Player),Hand)
doSomethingElse
- A
Playerrepeatedly submits aBetby invokingLotto.submit. - The argument of
submitis the objectBet(this(Player), Hand). - The first argument of
Betis a reference to thePlayersubmitting theBet. - The second argument of
Betis aHandwhich randomly generates 7 numbers. - After submitting a
Bet, it executesdoSomethingElsebefore playing the next time;doSomethingElseis not specified here.
The Lotto is represented by an object Lotto. This object keeps the bets being submitted, it has the winning bet, and the deadline for submitting bets. As players in parallel submit bets by calling the method submit, the Lotto object is defined as a MonitorProcess with as an entry method — similar to en submitentry-method of a Monitor object.
The structure of Lotto is as follows:
Lotto: obj MonitorProcess
submit(B: ref Bet): entry
bets.insert(B)
clearBets:
bets.clear
findWinningBets:
:::
bets: obj Set(#Bet)
:::
Lotto has the following attributes:
- An
entry-methodsubmit, which may be used byPlayerobjects tosubmitbets. As mentioned, it works in the same way as anentrymethod of aMonitor. This means that at most onesubmitmethod may be executed at a given time. - The
Betsbeing submitted are stored inbetswhich is aSet. - Methods
clearBetsandfindWinningBetsthat are private toLottoin the sense that they may not be invoked by objects (herePlayers) outsideLotto. As forMonitor, only methods being submethods ofentrymay be invoked from outsideLotto.
As said, a Lotto-period is a week. During a week the Players may submit bets. At the end of a week, Lotto stops accepting Bets via submit. It then invokes findWinningBets to find the possible winners of the week.
When possible winners have been found, Lotto informs the winners. It invokes clearBets to remove all elements from bets and open up for a new round of submissions. This is represented by the following statements of Lotto:
Lotto: obj MonitorProcess
-"-
run: do
waitAndAccept(aWeek)
findWinningBets
clearBets
restart(run)
The object run is executed forever:
- When a
MonitorProcess(hereLotto) is executing, it is not possible to execute anentry-method from outside. - The method
waitAndAcceptis defined as an attribute ofMonitorProcess. - When
waitAndAccept(aWeek), theMonitorProcess(Lotto) waits for a period – here defined byaWeekand while waiting it acceptsentry-methods likesubmit. - When
Lottohas waited for a week,waitAndAcceptresumes execution and closes for execution ofentry-methods likesubmit. - It then executes
findWinningBetsfollowed byclearBets.
When Lotto executes waitAndAccept, there may be Players that have invoked Lotto.submit. These invocations may be executed before waitAndAccept closes for execution of entry-methods. This means that a Player may submit a Bet after a week has passed. From a modeling point-of-view this may be ok since the invocation of submit has happened before a week has passed. If one does not consider this to be ok, the implementation of waitAndSubmit has to be able to block Players waiting to execute a submit.
We now show the details of findWinningBets:
findWinningBets:
winningBet := Bet(Player("Winner"), Hand)
bets.scan
if (current.equal(winningBet)) :then
"Winner: ".print
current.print
newline
- As mentioned, it starts by assigning
possibleToSubmitto false. - It then generates a
winningBetwith a hypotheticalPlayercalled “Winner” and aHandwith seven random numbers as arguments - It then scans the submitted bets in
betsand checks whether or not the currentBetis equal to thewinningBet - If a winner is found, the
Playerof thisBetis printed.
Finally we show the structure of class Hand and class Bet:
class Hand:
numbers: obj Array(betSize,#integer)
for (1):to(betSize):repeat
numbers.put(random(1,34)):at[inx]
class Bet(thePlayer: ref Player, theHand: ref Hand):
equal(aBet ref Bet) -> B: var boolean:
...
- Class
Handhas an arraynumbersthat contains the seven random numbers of theHand. - It uses a
for:to:repeatto generate and store seven random numbers innumbers. - Class
Bethas anequalmethod in addition to its two parameters.
For completeness, all the code for the Lotto example is shown below:
LottoExperiment: obj MonitorSystem
mnoOfPlayers: val 500
betSize: val 7
class Hand:
numbers: obj Array(betSize,#integer)
for (1):to(betSize):repeat
numbers.put(random(1,34)):at[inx]
class Bet(thePlayer: ref Player, theHand: ref Hand):
equal(aBet ref Bet) -> B: var boolean:
...
class Player(inx: var integer): MonitorProcess
cycle
Lotto.submit(Bet(this(Player),Hand)
doSomethingElse
Lotto: obj MonitorProcess
submit(B: ref Bet): entry
bets.insert(B)
clearBets:
bets.clear
findWinningBets:
winningBet := Bet(Player("Winner"), Hand)
bets.scan
if (current.equal(winningBet)) :then
"Winner: ".print
current.print
newline
bets: obj Set(#Bet)
run: do
waitAndAccept(aWeek)
findWinningBets
clearBets
restart(run)
Lotto.start
generatePlayers: do
...

