PAT Judge

PAT Judge
这个题没什么算法。。直接用sort就好了。
多关键字排序。

思路

看代码

/*
注意点:
 1.score高低排序。
 2.solved高低排序
 3.id高低排序
 4.输出时候,没有提交的问题输出-1,提交但是没编译通过的输出0;
 5.不应该输出没有提交或者没有编译通过的人。
 */
 
#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int max_n = 1e4;

int probMaxScore[10];
struct user
{
	// solved表示解决的问题数
	int id, solved;
	int totScore;
	// beShown代表当前用户最终是否出现在排行榜上。
	bool beShown;
	// probScore代表当前用户每个题的分数。
	// submitted代表当前用户每个题的提交情况,1是提交过,0是没提交。
	int probScore[10], submitted[10];
	user() {
		//构造函数初始化。
		solved = totScore = 0;
		beShown = false;
		memset(probScore, 0, sizeof(probScore));
		memset(submitted, 0, sizeof(submitted));
	}
	
	void update(int prob_id, int score) {
		// 如果这个问题还没有被提交,置1
		if (!submitted[prob_id]) 
			submitted[prob_id] = 1;
		//  如果编译没通过,不作处理。
		if (score == -1) return;
		// 编译通过,说明这个人可以被显示在排行榜。
		if (!beShown) beShown = true;
		int &score_ptr = probScore[prob_id];
		// 如果得分高于之前的得分
		if (score_ptr < score) {
			totScore += score - score_ptr;
			score_ptr = score;
			if (score == probMaxScore[prob_id]) solved++;
		}
	}
	// 多关键字排序,顺序见最上面。
	bool operator < (const user & u1) const {
		if (u1.totScore == totScore) {
			if (u1.solved == solved) 
				return id < u1.id;
			return solved > u1.solved;
		}
		return totScore > u1.totScore;
	}
	
} U[max_n + 10];

int N, K, M;
int main() {
	scanf("%d%d%d", &N, &K, &M);
	for (int i = 1; i <= K; i++) 
		scanf("%d", &probMaxScore[i]);

	for (int i = 1; i <= N; i++) U[i].id = i;

	for (int i = 0; i < M; i++) {
		int id, prob_id, score;
		scanf("%d%d%d", &id, &prob_id, &score);
		U[id].update(prob_id, score);
	}

	sort(U + 1, U + 1 + N);

    // Rank表示当前的排名,cnt表示用户数。
	int Rank = 0, cnt = 0, lst_score = -1;
	for (int i = 1; i <= N; i++) {
		if (!U[i].beShown) continue;
		cnt++;
		if (U[i].totScore != lst_score) 
			Rank = cnt;
        lst_score = U[i].totScore;
		printf("%d %05d %d ", Rank, U[i].id, U[i].totScore);
		for (int j = 1; j <= K; j++) {
			if (!U[i].submitted[j]) printf("-");
			else printf("%d", U[i].probScore[j]);
			if (j != K) printf(" ");
			else printf("\n");
		}
	} 
	return 0;
}

无注释版本。

#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int max_n = 1e4;

int probMaxScore[10];
struct user
{
	int id, solved;
	int totScore;
	bool beShown;
	int probScore[10], submitted[10];
	user() {
		solved = totScore = 0;
		beShown = false;
		memset(probScore, 0, sizeof(probScore));
		memset(submitted, 0, sizeof(submitted));
	}

	void update(int prob_id, int score) {
		if (!submitted[prob_id]) 
			submitted[prob_id] = 1;
		if (score == -1) return;
		if (!beShown) beShown = true;
		int &score_ptr = probScore[prob_id];

		if (score_ptr < score) {
			totScore += score - score_ptr;
			score_ptr = score;
			if (score == probMaxScore[prob_id]) solved++;
		}
	}
	bool operator < (const user & u1) const {
		if (u1.totScore == totScore) {
			if (u1.solved == solved) 
				return id < u1.id;
			return solved > u1.solved;
		}
		return totScore > u1.totScore;
	}
	
} U[max_n + 10];

int N, K, M;
int main() {
	scanf("%d%d%d", &N, &K, &M);
	
	for (int i = 1; i <= K; i++) 
		scanf("%d", &probMaxScore[i]);

	for (int i = 1; i <= N; i++) U[i].id = i;

	for (int i = 0; i < M; i++) {
		int id, prob_id, score;
		scanf("%d%d%d", &id, &prob_id, &score);
		U[id].update(prob_id, score);
	}

	sort(U + 1, U + 1 + N);
	
	int Rank = 0, cnt = 0, lst_score = -1;
	for (int i = 1; i <= N; i++) {
		if (!U[i].beShown) continue;
		cnt++;
		if (U[i].totScore != lst_score) 
			Rank = cnt;
        lst_score = U[i].totScore;
        
		printf("%d %05d %d ", 
			Rank, U[i].id, U[i].totScore);
			
		for (int j = 1; j <= K; j++) {
			if (!U[i].submitted[j]) 
				printf("-");
			else 
				printf("%d", U[i].probScore[j]);
			
			if (j != K) 
				printf(" ");
			else 
				printf("\n");
		}
	} 
	return 0;
}

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值