PAT甲级1114 Family Property:[C++题解]结构体、并查集、测试点3、4、5有问题的进来!!

本文主要是介绍PAT甲级1114 Family Property:[C++题解]结构体、并查集、测试点3、4、5有问题的进来!!,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

文章目录

    • 题目分析
    • 题目链接

题目分析

在这里插入图片描述
在这里插入图片描述
来源:acwing

分析:

  1. 先建边。读入每家的信息,在本人和父母(如果有的话),本人与子女(如果有的话)之间分别建边。边用结构体来存,边记录两个端点。
  2. 遍历每条边合并集合,分成一个一个家庭。这里的“遍历每条边”,指的是遍历两条边的端点(户主,或父母,或子女),利用find()函数合并,这里把id大的挂到id小的上面,这样,根结点就是答案所求的户主id。
  3. 将每个家庭存入vector,排序输出即可。为此,需要一个Family结构体,里面存户主id,家庭人数c,家庭房子数量hc,家庭房子面积ha,并重载小于号进行排序。

需要注意的点:

  1. 用int表示id,不用string。起初想用string来表示id,发现较为麻烦。原因有二,一是用string之后,用并查集之后还需要一步从string到int 的映射,教麻烦。二是题目明确每个id都是4位数,并且各不相同,这是变相地给我们降级难度,提示我们使用int。
  2. 家庭户主的id是编号最小的。由于我们是用并查集做的,这就提示我们只维护一个最小的id即可,其他id在统计到各个家庭之后没有什么用。在并查集中,合并的时候把较大的root接到较小的root上,这样得到的root就是最小的root。
  3. 前导0的输出,万能C语言!!!由于用int来存的id,如果像0004这样婶儿的,存的只是4,这就考验我们的格式化输出能力。使用printf("%04d",a);含义是以4位宽度输出数a,不足4位的在前面补0!

补充:printf("%4d",id)表示输出宽度为4,且右对齐,不足的在前面补空格。当变量的实际宽度大于4时,输出变量的所有数字.

ac代码

#include<bits/stdc++.h>
using namespace std;
const int N = 10010; //边的数量
int n;
int p[N]; //并查集父亲数组
int  c[N];//c[i]表示i这家人的人数 count
int hc[N];//房子数量 house count
int ha[N]; //房子面积 house area
bool st[N];// 户主 和父母,子女分别建边
struct Edge{int a, b;
}e[N];// 一家人放在一个结构体中,排序使用
struct Family{int id ,c ,hc, ha;bool operator<(const Family & t)const{// ha /c , t.ha/t.cif( ha * t.c != c * t.ha) return ha * t.c > c* t.ha;return id < t.id;}
};//并查集找根
int find(int x){if(p[x]!= x) p[x] = find(p[x]);return p[x];
}int main(){cin >>n;int m =0; //表示边数//第一部分: 读入所有输入,并建边for(int i = 0; i < n; i++){int id , father ,mother, k;cin >> id >> father >> mother >>k;//标记id出现过st[id] = true;if(father != -1) e[m++] = {id,father};if(mother != -1) e[m++] = {id,mother};for(int j = 0 ;j< k; j++){int son;cin >> son;e[m++] ={id,son};}cin >> hc[id] >> ha[id]; //房子数量,房子面积}//第二部分:得到每个家庭,并且户主编号最小//并查集初始化for(int i = 0; i<= N; i++) p[i] = i,c[i] =1 ;//i这家人只有1个人//遍历每条边:合并集合:得到每个家庭。for(int i = 0 ; i<m ;i++){int a = e[i].a, b = e[i].b;st[a] = st[b] = true; //标记每个点出现过//一个集合的根结点int pa = find(a),pb = find(b);//合并集合,让根结点大的集合挂到 根结点小的集合上!!//这样根结点就是编号最小的那个!!!//题目要求:ID 是家庭成员中编号最小的成员编号if(pa != pb){if(pb > pa) swap(pa,pb); //让pb成为较小的// 那么pb那个集合的值都要更新:加上pa集合的值//人数 , 房子数量,房子面积c[pb] += c[pa],hc[pb]+= hc[pa],ha[pb] += ha[pa];//pa集合挂到编号更小pb集合p[pa] = pb; }}// 第三部分:每个家庭的信息存起来,并输出vector<Family> familys;//遍历所有的点,如果之前出现过st[i] == true 并且是集合的根结点p[i] == i//代表i就是一家之主,将该家庭统计到vector中for(int i =0 ;i < N; i++){if(st[i] && p[i] == i)familys.push_back({i,c[i],hc[i],ha[i]});}//排序输出sort(familys.begin(),familys.end());cout<< familys.size()<<endl;for( auto f :familys){printf("%04d %d %.3lf %.3lf\n",f.id, f.c,(double)f.hc/f.c,(double)f.ha/f.c);}
}

在这里插入图片描述

注意:测试点3、4、5包括0000这个人。第一遍忽略了这个人,导致三个测试点错误。
在这里插入图片描述

题目链接

PAT甲级1114 Family Property
https://www.acwing.com/problem/content/1606/

这篇关于PAT甲级1114 Family Property:[C++题解]结构体、并查集、测试点3、4、5有问题的进来!!的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/465809

相关文章

关于@MapperScan和@ComponentScan的使用问题

《关于@MapperScan和@ComponentScan的使用问题》文章介绍了在使用`@MapperScan`和`@ComponentScan`时可能会遇到的包扫描冲突问题,并提供了解决方法,同时,... 目录@MapperScan和@ComponentScan的使用问题报错如下原因解决办法课外拓展总结@

MybatisGenerator文件生成不出对应文件的问题

《MybatisGenerator文件生成不出对应文件的问题》本文介绍了使用MybatisGenerator生成文件时遇到的问题及解决方法,主要步骤包括检查目标表是否存在、是否能连接到数据库、配置生成... 目录MyBATisGenerator 文件生成不出对应文件先在项目结构里引入“targetProje

C#使用HttpClient进行Post请求出现超时问题的解决及优化

《C#使用HttpClient进行Post请求出现超时问题的解决及优化》最近我的控制台程序发现有时候总是出现请求超时等问题,通常好几分钟最多只有3-4个请求,在使用apipost发现并发10个5分钟也... 目录优化结论单例HttpClient连接池耗尽和并发并发异步最终优化后优化结论我直接上优化结论吧,

Java内存泄漏问题的排查、优化与最佳实践

《Java内存泄漏问题的排查、优化与最佳实践》在Java开发中,内存泄漏是一个常见且令人头疼的问题,内存泄漏指的是程序在运行过程中,已经不再使用的对象没有被及时释放,从而导致内存占用不断增加,最终... 目录引言1. 什么是内存泄漏?常见的内存泄漏情况2. 如何排查 Java 中的内存泄漏?2.1 使用 J

numpy求解线性代数相关问题

《numpy求解线性代数相关问题》本文主要介绍了numpy求解线性代数相关问题,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧... 在numpy中有numpy.array类型和numpy.mat类型,前者是数组类型,后者是矩阵类型。数组

解决systemctl reload nginx重启Nginx服务报错:Job for nginx.service invalid问题

《解决systemctlreloadnginx重启Nginx服务报错:Jobfornginx.serviceinvalid问题》文章描述了通过`systemctlstatusnginx.se... 目录systemctl reload nginx重启Nginx服务报错:Job for nginx.javas

Redis缓存问题与缓存更新机制详解

《Redis缓存问题与缓存更新机制详解》本文主要介绍了缓存问题及其解决方案,包括缓存穿透、缓存击穿、缓存雪崩等问题的成因以及相应的预防和解决方法,同时,还详细探讨了缓存更新机制,包括不同情况下的缓存更... 目录一、缓存问题1.1 缓存穿透1.1.1 问题来源1.1.2 解决方案1.2 缓存击穿1.2.1

C++中实现调试日志输出

《C++中实现调试日志输出》在C++编程中,调试日志对于定位问题和优化代码至关重要,本文将介绍几种常用的调试日志输出方法,并教你如何在日志中添加时间戳,希望对大家有所帮助... 目录1. 使用 #ifdef _DEBUG 宏2. 加入时间戳:精确到毫秒3.Windows 和 MFC 中的调试日志方法MFC

vue解决子组件样式覆盖问题scoped deep

《vue解决子组件样式覆盖问题scopeddeep》文章主要介绍了在Vue项目中处理全局样式和局部样式的方法,包括使用scoped属性和深度选择器(/deep/)来覆盖子组件的样式,作者建议所有组件... 目录前言scoped分析deep分析使用总结所有组件必须加scoped父组件覆盖子组件使用deep前言

解决Cron定时任务中Pytest脚本无法发送邮件的问题

《解决Cron定时任务中Pytest脚本无法发送邮件的问题》文章探讨解决在Cron定时任务中运行Pytest脚本时邮件发送失败的问题,先优化环境变量,再检查Pytest邮件配置,接着配置文件确保SMT... 目录引言1. 环境变量优化:确保Cron任务可以正确执行解决方案:1.1. 创建一个脚本1.2. 修