TheAlgorithms/C++ 1.0.0
All the algorithms implemented in C++
Loading...
Searching...
No Matches
greedy_algorithms::stable_matching Namespace Reference

Functions for the Gale-Shapley Algorithm. More...

Functions

std::vector< std::uint32_t > gale_shapley (const std::vector< std::vector< std::uint32_t > > &secondary_preferences, const std::vector< std::vector< std::uint32_t > > &primary_preferences)
 The main function that finds the stable matching between two sets of elements using the Gale-Shapley Algorithm.
 

Detailed Description

Functions for the Gale-Shapley Algorithm.

Function Documentation

◆ gale_shapley()

std::vector< std::uint32_t > greedy_algorithms::stable_matching::gale_shapley ( const std::vector< std::vector< std::uint32_t > > & secondary_preferences,
const std::vector< std::vector< std::uint32_t > > & primary_preferences )

The main function that finds the stable matching between two sets of elements using the Gale-Shapley Algorithm.

Note
This doesn't work on negative preferences. the preferences should be continuous integers starting from 0 to number of preferences - 1.
Parameters
primary_preferencesthe preferences of the primary set should be a 2D vector
secondary_preferencesthe preferences of the secondary set should be a 2D vector
Returns
matches the stable matching between the two sets

Definition at line 46 of file gale_shapley.cpp.

48 {
49 std::uint32_t num_elements = secondary_preferences.size();
50 std::vector<std::uint32_t> matches(num_elements, -1);
51 std::vector<bool> is_free_primary(num_elements, true);
52 std::vector<std::uint32_t> proposal_index(
53 num_elements,
54 0); // Tracks the next secondary to propose for each primary
55
56 while (true) {
57 int free_primary_index = -1;
58
59 // Find the next free primary
60 for (std::uint32_t i = 0; i < num_elements; i++) {
61 if (is_free_primary[i]) {
62 free_primary_index = i;
63 break;
64 }
65 }
66
67 // If no free primary is found, break the loop
68 if (free_primary_index == -1)
69 break;
70
71 // Get the next secondary to propose
72 std::uint32_t secondary_to_propose =
73 primary_preferences[free_primary_index]
74 [proposal_index[free_primary_index]];
75 proposal_index[free_primary_index]++;
76
77 // Get the current match of the secondary
78 std::uint32_t current_match = matches[secondary_to_propose];
79
80 // If the secondary is free, match them
81 if (current_match == -1) {
82 matches[secondary_to_propose] = free_primary_index;
83 is_free_primary[free_primary_index] = false;
84 } else {
85 // Determine if the current match should be replaced
86 auto new_proposer_rank =
87 std::find(secondary_preferences[secondary_to_propose].begin(),
88 secondary_preferences[secondary_to_propose].end(),
89 free_primary_index);
90 auto current_match_rank =
91 std::find(secondary_preferences[secondary_to_propose].begin(),
92 secondary_preferences[secondary_to_propose].end(),
93 current_match);
94
95 // If the new proposer is preferred over the current match
96 if (new_proposer_rank < current_match_rank) {
97 matches[secondary_to_propose] = free_primary_index;
98 is_free_primary[free_primary_index] = false;
99 is_free_primary[current_match] =
100 true; // Current match is now free
101 }
102 }
103 }
104
105 return matches;
106}