Skip to content

Commit 14cc036

Browse files
committed
Allow attendees to won several times
... if there are more prizes than attendees
1 parent e716835 commit 14cc036

File tree

1 file changed

+29
-15
lines changed

1 file changed

+29
-15
lines changed

lib/raffle.js

Lines changed: 29 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
1-
21
class RaffleCandidate {
32
constructor(id, name, email, avatar) {
43
this._id = id;
54
this._name = name;
6-
this._email = email;
75
this._avatar = avatar;
86
}
97
}
@@ -30,9 +28,10 @@ class RaffleStatus {
3028

3129
class Raffle {
3230
constructor(candidates, prizes) {
33-
this._winners = new Set();
31+
this._results = new Set();
3432
this._candidates = candidates
3533
this._prizes = prizes;
34+
this._threshold = Math.ceil(this._prizes.length / this._candidates.length);
3635
}
3736

3837
run() {
@@ -41,37 +40,38 @@ class Raffle {
4140
}
4241
const candidates = this._filterCandidates();
4342
const winner = this._randomPick(candidates);
44-
this._winners.add(winner);
45-
return new RaffleResult(winner, this._prizes[this._winners.size - 1]);
43+
const prize = this._currentPrize();
44+
const result = new RaffleResult(winner, prize);
45+
this._results.add(result);
46+
return result;
4647
}
4748

4849
reset() {
49-
this._winners = new Set();
50+
this._results = new Set();
5051
}
5152

5253
status() {
53-
const results = Array.from(this._winners).map((winner, i) => new RaffleResult(winner, this._prizes[i]));
54-
return new RaffleStatus(results, this._isCompleted());
54+
return new RaffleStatus(Array.from(this._results), this._isCompleted());
5555
}
5656

5757
cancel(userId) {
58-
const user = this._findWinnerById(userId);
59-
if (!user) {
58+
const result = this._findResultByUserId(userId);
59+
if (!result) {
6060
return;
6161
}
62-
this._winners.delete(user);
62+
this._results.delete(result);
6363
}
6464

65-
_findWinnerById(userId) {
66-
return Array.from(this._winners).find((winner) => winner._id === userId);
65+
_findResultByUserId(userId) {
66+
return Array.from(this._results).find((result) => result._winner._id === userId);
6767
}
6868

6969
_isCompleted() {
70-
return this._winners.size === this._prizes.length;
70+
return this._results.size === this._prizes.length;
7171
}
7272

7373
_filterCandidates() {
74-
return this._candidates.filter((user) => !this._winners.has(user));
74+
return this._candidates.filter((user) => this._hasUserWonLessThan(user));
7575
}
7676

7777
_randomPick(candidates) {
@@ -80,6 +80,20 @@ class Raffle {
8080
}
8181
return candidates[Math.floor(Math.random() * Math.floor(candidates.length))];
8282
}
83+
84+
_hasUserWonLessThan(user) {
85+
let count = 0;
86+
this._results.forEach((result) => {
87+
if (result._winner === user && result._prize._description !== this._currentPrize()._description) {
88+
count++;
89+
}
90+
})
91+
return count < this._threshold;
92+
}
93+
94+
_currentPrize() {
95+
return this._prizes[this._results.size];
96+
}
8397
}
8498

8599
module.exports = {RaffleCandidate, RaffleWinner: RaffleResult, RafflePrize, Raffle};

0 commit comments

Comments
 (0)