Skip to content

Instantly share code, notes, and snippets.

@chapkovski
Last active February 23, 2019 10:47
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save chapkovski/24fd7ef33ae1d97d78058d9b2a7fe590 to your computer and use it in GitHub Desktop.
Save chapkovski/24fd7ef33ae1d97d78058d9b2a7fe590 to your computer and use it in GitHub Desktop.
Matching based on priorities
class GroupingWaitPage(WaitPage):
_allow_custom_attributes = True
group_by_arrival_time = True
def get_unique(self, wp, priority, filtering=None, matched=None):
seen = set()
# we don't need to re-use matched players
if matched:
wp = [w for w in wp if w not in matched]
# we need to filter the waiting players if we want to get rid of the priorities used in some other list
if filtering:
wp = [w for w in wp if w.participant.vars[priority] not in filtering]
uniques = [p for p in wp if
p.participant.vars[priority] not in seen and not seen.add(p.participant.vars[priority])]
return uniques
def get_players_for_group(self, waiting_players):
group_size = 3
stopper = 6 # when the number of waiting players reach a certain threshold we start grouping them based on
# their non-first priorities.
# The next line just a naive break if there are no one to wait for anymore: then we match them randomly.
slowpokes = [p for p in self.session.get_participants() if p._index_in_pages < self._index_in_pages]
if len(slowpokes) == 0 and len(waiting_players) >= group_size:
return waiting_players[:group_size]
unique_1 = self.get_unique(waiting_players, 'first')
if len(unique_1) >= group_size:
return unique_1[:group_size]
if len(waiting_players) >= stopper:
# we need to find the lacking element in the second priorites to add missing one(s) to a first priority list
priorities_1 = [w.participant.vars['first'] for w in unique_1]
unique_2 = self.get_unique(waiting_players, 'second', filtering=priorities_1, matched=unique_1)
unique_1_2 = unique_1 + unique_2
if len(unique_1_2) >= group_size:
return unique_1_2[:group_size]
priorities_2 = [w.participant.vars['second'] for w in unique_2]
unique_1_2_3 = unique_1_2 + self.get_unique(waiting_players, 'third', filtering=priorities_1 + priorities_2,
matched=unique_1_2)
return unique_1_2_3[:group_size]
@chapkovski
Copy link
Author

It is built on the assumption that:

  1. Number of priorities equals 3.

  2. Each member in the group should ideally have a unique top priority. If something more complicated need (like 2 journalists, 1 economist), the code needs adjustment

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment