PAT 甲级 1114 Family Property (25 分)

思路:

1.用结构体将每一个人的信息存储下来,同时将每一个人的家人也作为一个人存储下来,为了使用这些人的家人部分;
2.设立map标记某一个人是否被遍历过、是否在输入给定的人里(每行输入的第一个id)(为了确定遍历到这个人时要不要加上他的资产);
3.将人以id为key存入map,从头开始遍历,可以解决家族中输出id最小的问题;
4.设立家族结构体,储存相应变量,并编写相应排序规则,每遍历完一个家族,将其存入set;
5.最后以"%04d %d %.3f %.3f "格式输出;

代码:

#include<iostream>
#include<map>
#include<vector>
#include<set>
using namespace std;
struct person{
	int m,area;
	vector<int> v;
};
struct family{
	int id,m;
	double sets,area;
	bool operator < (const family & f) const{
		return area==f.area?id<f.id:area>f.area;
	}
};
int n,m,sets,area;
map<int,bool> checked,exist;
map<int,person> mp;
set<family> st;
void traversal(int p){
	checked[p]=true;
	m++;
	if(exist[p]){
		sets+=mp[p].m;
		area+=mp[p].area;
	}
	for(auto e:mp[p].v)
		if(!checked[e]&&~e) traversal(e);
}
int main(){
	scanf("%d",&n);
	for(int i=0;i<n;i++){
		int id,k,chd;
		vector<int> v(2);
		scanf("%d%d%d%d",&id,&v[0],&v[1],&k);
		exist[id]=true;
		for(int j=0;j<k;j++){
			scanf("%d",&chd);
			v.push_back(chd);
			mp[id].v=v;
			for(auto e:v) mp[e].v.push_back(id);
		}
		scanf("%d%d",&mp[id].m,&mp[id].area);
	}
	for(auto e:mp){
		if(!checked[e.first]&&~e.first){
			m=sets=area=0;
			traversal(e.first);
			family f{e.first,m,sets/(m*1.0),area/(m*1.0)};
			st.insert(f);
		}
	}
	printf("%d
",st.size());
	for(set<family>::iterator it=st.begin();it!=st.end();it++)
		printf("%04d %d %.3f %.3f
",it->id,it->m,it->sets,it->area);
	return 0;
}
原文地址:https://www.cnblogs.com/yuhan-blog/p/12309014.html