PAT乙级1015 德才论

这题····awsl
上代码

#include<stdio.h>
#include<string.h>
typedef struct student {
	char id[9];
	int de, cai;
};
void partition(student A[], int a, int n);
student Stu[100001], StuA[100001], StuB[100001], StuC[100001], StuD[100001];

int main() {
	int n, l, h, i = 1, count = 0, ca = 1,cb = 1,cc=1,cd=1;
	void equ(student * A, student B);
	void sort(student A[],int a);
	void print(student S[],int n);
	scanf("%d %d %d", &n, &l, &h);
	while (i <= n) {
		scanf("%s", Stu[i].id);
		scanf("%d %d", &Stu[i].de, &Stu[i].cai);
		if (Stu[i].de >= l && Stu[i].cai >= l) {
			count++;
			if (Stu[i].de >= h && Stu[i].cai >= h) {
				equ(&StuA[ca], Stu[i]);
				ca++;
			}
			else if (Stu[i].de >=h ){
				equ(&StuB[cb], Stu[i]);
				cb++;
			}
			else if (Stu[i].de >= Stu[i].cai) {
				equ(&StuC[cc], Stu[i]);
				cc++;
			}
			else {
				equ(&StuD[cd], Stu[i]);
				cd++;
			}
		}
		i++;
	
	}
	sort(StuA, ca);
	sort(StuB, cb);
	sort(StuC, cc);
	sort(StuD, cd);
	printf("%d\n",ca + cb + cc+cd-4);
	print(StuA, ca-1);
	print(StuB, cb-1);
	print(StuC, cc-1);
	print(StuD, cd-1);
	return 0;
}



void equ(student* A, student B) {
	A->cai = B.cai;
	A->de = B.de;
	strcpy(A->id, B.id);
}

void sort(student A[],int a) {
	student temp;
	partition(A,1,a-1);
	for (int j = 1; j < a; j++) {
		for (int i = 1; i < a ; i++) {
			if (A[i].cai + A[i].de == A[i + 1].cai + A[i + 1].de) {
				if (A[i].de < A[i + 1].de) {
					equ(&temp, A[i]);
					equ(&A[i], A[i + 1]);
					equ(&A[i+1], temp);
				}
				else if (A[i].de == A[i + 1].de) {
					if (strcmp(A[i].id, A[i + 1].id) > 0) {
						equ(&temp, A[i]);
						equ(&A[i], A[i + 1]);
						equ(&A[i+1], temp);
					}
				}
			}
		}
	}

}

void print(student S[],int n){
	for (int i = 1; i <= n; i++) {
		for (int j = 0; j < 8; j++)
			printf("%c", S[i].id[j]);
		printf(" %d %d\n", S[i].de, S[i].cai);
	}
}
//main函数堆栈溢出解决办法:将数组定义在main外

void partition(student S[],int a,int n) {
	if (a >= n) return;
	student temp=S[a];
	int i = a, j = n;
	while (i<j) {
		while (temp.cai + temp.de >= S[j].cai + S[j].de) {
			if (j <= i) break;
			j--;
			
		}
		equ(&S[i], S[j]);
		while (temp.cai + temp.de < S[i].cai + S[i].de) {
			if (j <= i) break;
			i++;
			
		}
		equ(&S[j], S[i]);
	}
	equ(&S[i], temp);
	partition(S,1,i-1);
	partition(S, i + 1, n);
}

 第一次用了冒泡排序,运行超时。
 改为快排,但是快排不能确定哪一个在前,所以同分情况仍然使用冒泡排序,运行超时。
在这里插入图片描述
 接下来考虑重载运算符>,分三种情况讨论

  1. 如果de+cai不同,则de+cai大的大
  2. de+cai相同,则de大
  3. de也相同,则id大的小

 也即,采用这种方式之后,应该是从大到小输出。
 分析题目,输入时需要O(n)时间,排序加输出,最少的时间复杂度应该为O(nlongn)也就是快排,归并,堆排序。运算符重载之后,不存在两个相等的情况,三种都可以输出正确的序列。
上代码:

#include<stdio.h>
#include<string.h>
using namespace std;

class student {
public:
	char id[9];
	int de, cai;
	student operator =(student a) {
		this->cai= a.cai;
		this->de=a.de;
		strcpy(this->id, a.id);
		return *this;
	}
};

bool operator >(student a,student b) {
	if (a.cai + a.de < b.cai + b.de) return false;
	else if (a.cai + a.de > b.cai + b.de) return true;
	else if (a.cai + a.de == b.cai + b.de) {
		if (a.de > b.de) return true;
		else if (a.de < b.de) return false;
		else if (strcmp(a.id, b.id) < 0) return true;
		else return false;
	}
}

student Stu, StuA[100001], StuB[100001], StuC[100001], StuD[100001];

int main(){
	int n, l, h, i = 1, count = 0, ca = 1,cb = 1,cc=1,cd=1;
	void equ(student * A, student B);
	void sort(student A[],int a);
	void print(student S[],int n);
	scanf("%d %d %d", &n, &l, &h);
	while (i <= n) {
		scanf("%s", Stu.id);
		scanf("%d %d", &Stu.de, &Stu.cai);
		if (Stu.de >= l && Stu.cai >= l) {
			count++;
			if (Stu.de >= h && Stu.cai >= h) {
				StuA[ca]=Stu;
				ca++;
			}
			else if (Stu.de>=h ){
				StuB[cb] = Stu;
				cb++;
			}
			else if (Stu.de >= Stu.cai) {
				StuC[cc] = Stu;
				cc++;
			}
			else {
				StuD[cd] = Stu;
				cd++;
			}
		}
		i++;
	
	}
	sort(StuA, ca);
	sort(StuB, cb);
	sort(StuC, cc);
	sort(StuD, cd);
	printf("%d\n",count);
	print(StuA, ca-1);
	print(StuB, cb-1);
	print(StuC, cc-1);
	print(StuD, cd-1);
	return 0;
}

void print(student S[],int n){
	for (int i = 1; i <= n; i++) {
		for (int j = 0; j < 8; j++)
			printf("%c", S[i].id[j]);
		printf(" %d %d\n", S[i].de, S[i].cai);
	}
}
//main函数堆栈溢出解决办法:将数组定义在main外

void sort(student A[], int a) {
    void partition(student S[],int a,int n) ;
	student temp;
	partition(A, 1, a - 1);
}

void partition(student S[],int a,int n) {
	if (a >= n) return;
	student temp=S[a];
	int i = a, j = n;
	while (i<j) {
		while (temp>S[j]) {
			if (j <= i) break;
			j--;
		}
		S[i] = S[j];
		while (S[i]>temp) {
			if (j <= i) break;
			i++;
		}
		S[j]=S[i];
	}
	S[i]=temp;
	partition(S,1,i-1);
	partition(S, i + 1, n);
}

仍然超时,我秃了


终于!看到了大神的代码。大神代码
总体看来没有很大的差别,除了排序函数不一样。这个版本的排序函数是用的c++/c头文件中自带的sort函数
改过之后代码如下:

#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;

class student {
public:
	int id;
	int de, cai;
	student operator =(student a) {
		this->cai= a.cai;
		this->de=a.de;
		this->id=a.id;
		return *this;
	}
};

bool Cmp(student a,student b) {
	if ((a.de + a.cai) != (b.de + b.cai)) 
		return a.de + a.cai > b.de + b.cai;
	else                                  
	{
		if (a.de != b.de)
			return a.de > b.de;
		else
			return a.id<b.id; 
	}
}

student Stu, StuA[100001], StuB[100001], StuC[100001], StuD[100001];

int main(){
	int n, l, h, i = 1, count = 0, ca = 1,cb = 1,cc=1,cd=1;
	void equ(student * A, student B);
	void print(student S[],int n);
	scanf("%d %d %d", &n, &l, &h);
	while (i <= n) {
		scanf("%d %d %d", &Stu.id,&Stu.de, &Stu.cai);
		if (Stu.de >= l && Stu.cai >= l) {
			count++;
			if (Stu.de >= h && Stu.cai >= h) {
				StuA[ca]=Stu;
				ca++;
			}
			else if (Stu.de>=h ){
				StuB[cb] = Stu;
				cb++;
			}
			else if (Stu.de >= Stu.cai) {
				StuC[cc] = Stu;
				cc++;
			}
			else {
				StuD[cd] = Stu;
				cd++;
			}
		}
		i++;
	}
	sort(&StuA[1],&StuA[ca], Cmp);
	sort(&StuB[1], &StuB[cb], Cmp);
	sort(&StuC[1], &StuC[cc], Cmp);
	sort(&StuD[1], &StuD[cd], Cmp);
	printf("%d\n",count);
	print(StuA, ca-1);
	print(StuB, cb-1);
	print(StuC, cc-1);
	print(StuD, cd-1);
	return 0;
}

void print(student S[],int n){
	for(int i=1;i<=n;i++)
		printf("%d %d %d\n", S[i].id,S[i].de, S[i].cai);
}
//main函数堆栈溢出解决办法:将数组定义在main外

在这里插入图片描述
另外还有人使用qsort函数,也是自带的函数。这个差别可能是partition函数不一样造成的。
给自己码一个

  • qsort函数文档。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值