UVa 10142 - Australian Voting

题目:澳大利亚选举,有n个候选人m个公民,每个公民对每个候选人有一个期望的优先级,

选举时,先按第一优先级分配选票,得票最少的候选人的投票,将按投票人的优先级,

重新分给留下的候选人,直到某人获得50%或以上的选票,或者剩下的人得票相同,

求选举结果。

分析:模拟。按照上述规则模拟即可,过程有点麻烦。

说明:数据给事有点恶心,注意到达50%就可以认为胜利了,不用超过╮(╯▽╰)╭。

#include <algorithm>
#include <iostream>
#include <cstdlib>
#include <cstring>
#include <cstdio>

using namespace std;

char candidate[21][81];
char buf[1001];
int  choice[1001][21];
int  vote[21][1001];
int  vote_size[21];

int main()
{
	int t,n;
	while (~scanf("%d",&t))
	while (t --) {
		scanf("%d",&n);
		getchar();
		for (int i = 0; i < n; ++ i) {
			gets(candidate[i]);
			vote_size[i] = 0;
		}
		//提取每个公民的投票意向
		int number = 0;
		while (gets(buf) && buf[0]) {
			int value = 0, count = 0;
			for (int i = 0; buf[i]; ++ i)
				if (buf[i] >= '0' && buf[i] <= '9') {
					value *= 10;
					value += buf[i]-'0';
				}else {
					choice[number][count ++] = value-1;
					value = 0;
				}
			choice[number ++][count ++] = value-1;
		}
		//初始化
		for (int i = 0; i < number; ++ i) {
			int cand = choice[i][0];
			vote[cand][vote_size[cand] ++] = i;
		}

		while (1) {
			int max = 0, min = 1001, max_space, min_space;
			for (int i = 0; i < n; ++ i)
				if (vote_size[i]) {
					if (max < vote_size[i]) {
						max = vote_size[i];
						max_space = i;
					}
					if (min > vote_size[i]) {
						min = vote_size[i];
						min_space = i;
					}
				}
			if (max*2 >= number) break;//等于 50%也可以
			if (max == min) break;
			for (int k = 0; k < n; ++ k) {
				if (vote_size[k] != min) continue;
				//取出得票最少的人的选票s
				for (int i = 0; i < vote_size[k]; ++ i) {
					int per = vote[k][i];
					//重新按意向分配当前公民选票
					for (int j = 0; j < n; ++ j) {
						int can = choice[per][j];
						if (vote_size[can] != min && vote_size[can]) {
							vote[can][vote_size[can] ++] = per;
							break;
						}
					}
				}
				vote_size[k] = 0;
			}
		}

		int max_space = 0;
		for (int i = 0; i < n; ++ i)
			if (vote_size[max_space] < vote_size[i])
				max_space = i;
		for (int i = 0; i < n; ++ i)
			if (vote_size[max_space] == vote_size[i])
				puts(candidate[i]);
		if (t) puts("");
	}
    return 0;
}

一些测试数据:

2

3
John Doe
Jane Smith
Sirhan Sirhan
1 2 3
2 1 3
2 3 1
1 2 3
3 1 2

3
John Doe
Jane Smith
Sirhan Sirhan
1 2 3
2 1 3
2 3 1
1 2 3

1

4
A
B
C
D
2 1 3 4
2 1 3 4
3 1 4 2
4 1 2 3

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-10-11 22:49:47

UVa 10142 - Australian Voting的相关文章

UVA 10142 Australian Voting(模拟)

题意:澳大利亚投票系统要求选民们将所有候选人按愿意选择的程度排序,一张选票就是一个排序.一开始,每张选票的首选项将被统计.若有候选人得票超过50%,他讲直接胜出:否则,所有并列最低的候选人出局,而那些将出局候选人排在第一位的选票将被重新统计为排名最高的未出局候选人.这一筛选过程将持续进行,直到某个候选人得到超过50%的选票,或所有候选人得票相同. #include<cstdio> #include<cstring> #include<iostream> #include

编程题目分类(剪辑)

1. 编程入门 2. 数据结构 3. 字符串 4. 排序 5. 图遍历 6. 图算法 7. 搜索:剪枝,启发式搜索 8. 动态规划/递推 9. 分治/递归 10. 贪心 11. 模拟 12. 算术与代数 13. 组合问题 14. 数论 15. 网格,几何,计算几何 [编程入门] PC 110101, uva 100, The 3n+1 problem, 难度 1 PC 110102, uva 10189, Minesweeper, 难度 1 PC 110103, uva 10137, The T

计划,,留

下面给出的题目共计560道,去掉重复的也有近500题,作为ACMer Training Step1,用1年到1年半年时间完成.打牢基础,厚积薄发. 一.UVaOJ http://uva.onlinejudge.org 西班牙Valladolid大学的程序在线评测系统,是历史最悠久.最著名的OJ. 一.<算法竞赛入门经典> 刘汝佳 (UVaOJ 351道题) 以下部分内容摘自:http://sdkdacm.5d6d.com/thread-6-1-1.html "AOAPC I"

算法竞赛入门经典+挑战编程+USACO

下面给出的题目共计560道,去掉重复的也有近500题,作为ACMer Training Step1,用1年到1年半年时间完成.打牢基础,厚积薄发.   一.UVaOJ http://uva.onlinejudge.org  西班牙Valladolid大学的程序在线评测系统,是历史最悠久.最著名的OJ.   二.<算法竞赛入门经典> 刘汝佳  (UVaOJ  351道题)  以下部分内容摘自:http://sdkdacm.5d6d.com/thread-6-1-1.html   "AO

(Step1-500题)UVaOJ+算法竞赛入门经典+挑战编程+USACO

下面给出的题目共计560道,去掉重复的也有近500题,作为ACMer Training Step1,用1年到1年半年时间完成.打牢基础,厚积薄发. 一.UVaOJ http://uva.onlinejudge.org 西班牙Valladolid大学的程序在线评测系统,是历史最悠久.最著名的OJ. 二.<算法竞赛入门经典> 刘汝佳  (UVaOJ  351道题)  以下部分内容摘自:http://sdkdacm.5d6d.com/thread-6-1-1.html “AOAPC I”是刘汝佳(大

queue/prioity_queue

queue/prioity_queue uva,144 1-25个学生,每人每年领40美元.一个防盗的atm机按照1.2...k的方式依次吐出硬币. 例如:第一次吐出1coin,第二次吐出2 coins 直到限制k.然后循环从1开始吐.学生插卡取钱,当达到限额就离开队列. 注意:只有当output store没钱了,才会向里面吐钱.所以每次学生最大领的钱数为k.没领到40继续排在末尾. 1 #include <iostream> 2 #include <cstdio> 3 #inc

HOJ 题目分类

转自:http://blog.sina.com.cn/s/blog_65f3869301011a1o.html ******************************************************************************* 简单题(包括枚举,二分查找,(复杂)模拟,基础数据结构(栈.队列),杂题等 ****************************************************************************

UVA 562 Dividing coins --01背包的变形

01背包的变形. 先算出硬币面值的总和,然后此题变成求背包容量为V=sum/2时,能装的最多的硬币,然后将剩余的面值和它相减取一个绝对值就是最小的差值. 代码: #include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> using namespace std; #define N 50007 int c[102],d

UVA 10341 Solve It

Problem F Solve It Input: standard input Output: standard output Time Limit: 1 second Memory Limit: 32 MB Solve the equation: p*e-x + q*sin(x) + r*cos(x) + s*tan(x) + t*x2 + u = 0 where 0 <= x <= 1. Input Input consists of multiple test cases and te