Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- <?php
- // number of winners
- $max_winners = 10;
- // seed mersenne twister with fixed value
- mt_srand(12345);
- // read entries
- $entries = readlines("entries.txt");
- // read votes
- $votes = array();
- $votefiles = scandir("votes");
- foreach($votefiles as $file) {
- if(preg_match("/\.txt$/", $file))
- $votes[basename($file, ".txt")] = readlines("votes/" . $file);
- }
- echo "Entries:\n";
- print_r($entries);
- echo "Votes:\n";
- print_r($votes);
- // calculate winners
- $winners = repeated_instant_runoff_vote($entries, $votes, min($max_winners, count($entries)));
- // print result
- echo "#################### All winners ####################\n";
- print_r($winners);
- function readlines($file) {
- $lines = explode("\n", file_get_contents($file));
- $ret = array();
- foreach($lines as $line) {
- $l = trim($line);
- if($l != "")
- $ret[] = $l;
- }
- return $ret;
- }
- function random_real($a, $b) {
- return $a + ($b - $a) * mt_rand() / mt_getrandmax();
- }
- function repeated_instant_runoff_vote($entries, $votes, $repeats) {
- // make sure all votes are valid
- foreach($votes as $voter => $vote) {
- foreach($vote as $e) {
- if(!in_array($e, $entries)) {
- die("Error: invalid vote for '$e' from '$voter'!\n");
- }
- }
- }
- // one more winner and one less candidate after each iteration
- $candidates = array_fill_keys($entries, 0);
- $winners = array();
- for($rep = 0; $rep < $repeats; ++$rep) {
- echo "#################### Winner " . ($rep + 1) . " ####################\n";
- // start voting
- $candidates_left = $candidates;
- while(count($candidates_left) > 1) {
- // count votes
- $scores = $candidates_left;
- foreach($votes as $vote) {
- foreach($vote as $e) {
- if(isset($scores[$e])) {
- ++$scores[$e];
- break;
- }
- }
- }
- // random tie-breaker
- foreach($scores as &$s) {
- $s += random_real(0.01, 0.09);
- }
- unset($s);
- // sort and eliminate the candidate with the lowest score
- arsort($scores);
- end($scores);
- $eliminate = key($scores);
- unset($candidates_left[$eliminate]);
- print_r($scores);
- echo "'" . $eliminate . "' eliminated.\n";
- }
- // get the winner
- reset($candidates_left);
- $winner = key($candidates_left);
- unset($candidates[$winner]);
- $winners[] = $winner;
- echo "=> Winner " . ($rep + 1) . " is '" . $winner . "'\n";
- }
- return $winners;
- }
- ?>
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement