AtCoder Beginner Contest 181 题解
总结
第一次 \(AK\ ABC\) 的比赛,发一个截图纪念一下
A - Heavy Rotation
题目大意
一个人一开始穿白衣服,一天后换成黑衣服,再过一天又换成白衣服,问第 \(n(n \leq 30)\) 天这个人穿什么颜色的衣服
分析
当 \(n\) 为奇数时输出 \(Black\),否则输出 \(White\)
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define rg register
inline int read(){
rg int x=0,fh=1;
rg char ch=getchar();
while(ch<'0' || ch>'9'){
if(ch=='-') fh=-1;
ch=getchar();
}
while(ch>='0' && ch<='9'){
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*fh;
}
const int maxn=1e5+5;
int main(){
int n;
scanf("%d",&n);
if(n&1) printf("Black\n");
else printf("White\n");
return 0;
}
B - Trapezoid Sum
题目大意
给出 \(n(1 \leq n \leq 10^5)\) 次操作
每次操作加上 \(a \sim b(1 \leq a \leq b \leq 10^6)\) 这个区间内所有数之和
问最终的答案是多少
分析
用等差数列求和公式即可解决
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define rg register
inline int read(){
rg int x=0,fh=1;
rg char ch=getchar();
while(ch<'0' || ch>'9'){
if(ch=='-') fh=-1;
ch=getchar();
}
while(ch>='0' && ch<='9'){
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*fh;
}
const int maxn=1e5+5;
int n;
int main(){
n=read();
long long sum=0;
rg int aa,bb;
for(rg int i=1;i<=n;i++){
aa=read(),bb=read();
sum+=1LL*(aa+bb)*(bb-aa+1)/2LL;
}
printf("%lld\n",sum);
return 0;
}
C - Collinearity
题目大意
有 \(n\) 个点,第 \(i\) 个点坐标为 \((x_i,y_i)\),判断是否存在三点共线。
\(3≤n≤100,|x_i|,|y_i|≤10^3\),任意两点坐标均不相同。
分析
每次取出两个点,求出直线的解析式,再从其他点中找有没有符合这个解析式的
要把横坐标相等的特判一下
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<map>
#define rg register
inline int read(){
rg int x=0,fh=1;
rg char ch=getchar();
while(ch<'0' || ch>'9'){
if(ch=='-') fh=-1;
ch=getchar();
}
while(ch>='0' && ch<='9'){
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*fh;
}
const int maxn=1e2+5;
int n,x[maxn],y[maxn];
std::map<int,int> mp;
int main(){
n=read();
bool jud=0;
for(rg int i=1;i<=n;i++){
x[i]=read(),y[i]=read();
}
for(rg int i=1;i<=n;i++){
for(rg int j=i+1;j<=n;j++){
if(x[i]==x[j]) continue;
double k=(double)(y[i]-y[j])/(x[i]-x[j]);
double b=y[i]-k*x[i];
rg int cnt=2;
for(rg int kk=1;kk<=n;kk++){
if(i==kk || j==kk) continue;
if(x[kk]*k+b==y[kk]) cnt++;
}
if(cnt>=3) jud=1;
}
}
for(rg int i=1;i<=n;i++){
mp[x[i]]++;
if(mp[x[i]]>=3) jud=1;
}
if(jud) printf("Yes\n");
else printf("No\n");
return 0;
}
D - Hachi
题目大意
给一个长度为 \(s\) 的数字,判断这个数字在任意交换数位后是否存在一个可以被 \(8\) 整除的数。
\(1≤s≤200000\),每位数字均在 \([1,9]\) 之间。
分析
要判断一个数字能否被 \(8\) 整除,只需要判断它的后三位能否被 \(8\) 整除
因为 \(1000\) 的倍数肯定是 \(8\) 的倍数
那么我们只要从 \(0\) 到 \(1000\) 枚举 \(8\) 的倍数,判断从给定的数字中选取一些数能否组成 \(8\) 的倍数即可
要把长度小于 \(3\) 的数字特判一下
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<map>
#define rg register
inline int read(){
rg int x=0,fh=1;
rg char ch=getchar();
while(ch<'0' || ch>'9'){
if(ch=='-') fh=-1;
ch=getchar();
}
while(ch>='0' && ch<='9'){
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*fh;
}
const int maxn=1e6+5;
char s[maxn];
int len,cnt[maxn],ncnt[maxn],ans,a[maxn];
int main(){
scanf("%s",s+1);
len=strlen(s+1);
bool jud=0;
if(len<=3){
int mi=1,nans=0;
for(rg int i=1;i<=len;i++){
a[i]=s[i]-'0';
}
std::sort(a+1,a+1+len);
while(1){
mi=1;
nans=0;
for(rg int j=1;j<=len;j++){
nans+=a[j]*mi;
mi*=10;
}
if(nans%8==0) jud=1;
if(std::next_permutation(a+1,a+1+len)==0) break;
}
} else {
for(rg int i=1;i<=len;i++){
cnt[s[i]-'0']++;
}
for(rg int i=100;i<=1000;i++){
if(i%8) continue;
for(rg int j=0;j<=9;j++) ncnt[j]=0;
rg int now=i;
while(now){
ncnt[now%10]++;
now/=10;
}
bool pd=1;
for(rg int j=0;j<=9;j++){
if(cnt[j]<ncnt[j]) pd=0;
}
if(pd) jud=1;
}
}
if(jud) printf("Yes\n");
else printf("No\n");
return 0;
}
E - Transformable Teacher
题目大意
有 \(n\)(\(n\) 为奇数) 个小朋友和 \(m\)个老师,每个人都有自己的权值。
现在要选出 \(1\) 位老师给小朋友们上课,并将小朋友们两两分组。
请选出一个选老师和分组的方案,使得所有组两人权值之差的绝对值之和最小。
分析
显然排序之后的答案一定是最小的
那么我们可以先将所有的小朋友按照身高从小到大排好序
对于每一位老师,二分枚举他的位置
因为老师的插入最多只会改变两组小朋友的匹配
所以我们要预处理出从第一个小朋友开始匹配的答案的前缀和以及从第二个小朋友开始匹配的答案的前缀和
这样就可以 \(O(1)\) 计算答案
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<map>
#define rg register
inline int read(){
rg int x=0,fh=1;
rg char ch=getchar();
while(ch<'0' || ch>'9'){
if(ch=='-') fh=-1;
ch=getchar();
}
while(ch>='0' && ch<='9'){
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*fh;
}
const int maxn=1e6+5;
int h[maxn],w[maxn],n,m;
long long sum1[maxn],sum2[maxn];
int main(){
n=read(),m=read();
for(rg int i=1;i<=n;i++){
h[i]=read();
}
std::sort(h+1,h+1+n);
for(rg int i=1;i<=m;i++){
w[i]=read();
}
for(rg int i=1;i<=n/2;i++){
sum1[i]=sum1[i-1]+h[i*2]-h[i*2-1];
}
for(rg int i=1;i<=n/2;i++){
sum2[i]=sum2[i-1]+h[i*2+1]-h[i*2];
}
rg long long ans=0x3f3f3f3f3f3f3f3f;
for(rg int i=1;i<=m;i++){
if(w[i]>h[n]){
ans=std::min(ans,w[i]-h[n]+sum1[n/2]);
} else {
rg int wz=std::upper_bound(h+1,h+1+n,w[i])-h;
if(wz&1) ans=std::min(ans,sum1[wz/2]+h[wz]-w[i]+sum2[n/2]-sum2[wz/2]);
else ans=std::min(ans,sum1[(wz-1)/2]+w[i]-h[wz-1]+sum2[n/2]-sum2[(wz-1)/2]);
}
}
printf("%lld\n",ans);
return 0;
}
F - Silver Woods
题目大意
平面上有 \(n\) 个点,现在你有一个半径待定的圆,且初始时圆心位于 \((−10^9,0)\)。
你需要最大化圆的半径,且满足这个圆能穿通过移动,直到圆心到达 \((10^9,0)\)。
在移动的过程中圆不能与直线 $y=10$0
或直线 \(y=−100\) 相交,且任何时候这 \(n\)个点都不在圆内。
\(n≤100,|xi|,|yi|≤100\)。
分析
二分圆的半径,利用并查集维护距离小于等于当前二分的答案的点的集合
对于每一个集合,判断其是否将道路封住
如果没有就合法,否则不合法
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<map>
#define rg register
inline int read(){
rg int x=0,fh=1;
rg char ch=getchar();
while(ch<'0' || ch>'9'){
if(ch=='-') fh=-1;
ch=getchar();
}
while(ch>='0' && ch<='9'){
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*fh;
}
const int maxn=1e3+5;
typedef double db;
const db eps=1e-10;
db x[maxn],y[maxn],dis[maxn][maxn],mmin[maxn],mmax[maxn];
int n,fa[maxn];
int zhao(int xx){
if(xx==fa[xx]) return xx;
return fa[xx]=zhao(fa[xx]);
}
bool jud(db val){
for(rg int i=1;i<=n;i++){
fa[i]=i;
mmin[i]=std::max(-100.0,y[i]-val*2.0);
mmax[i]=std::min(100.0,y[i]+val*2.0);
}
for(rg int i=1;i<=n;i++){
for(rg int j=i+1;j<=n;j++){
rg int aa=zhao(i),bb=zhao(j);
if(aa==bb) continue;
if(dis[i][j]>2.0*val) continue;
fa[bb]=aa;
mmin[aa]=std::min(mmin[aa],mmin[bb]);
mmax[aa]=std::max(mmax[aa],mmax[bb]);
}
}
for(rg int i=1;i<=n;i++){
if(fa[i]==i){
if(mmin[i]==-100.0 && mmax[i]==100.0) return 0;
}
}
return 1;
}
int main(){
scanf("%d",&n);
for(rg int i=1;i<=n;i++){
scanf("%lf%lf",&x[i],&y[i]);
}
for(rg int i=1;i<=n;i++){
for(rg int j=1;j<=n;j++){
dis[i][j]=(db)sqrt((x[i]-x[j])*(x[i]-x[j])+(y[i]-y[j])*(y[i]-y[j]));
}
}
rg db l=0.0,r=100.0,mids;
while(r-l>eps){
mids=(l+r)/2.0;
if(jud(mids)) l=mids;
else r=mids;
}
printf("%.6f\n",mids);
return 0;
}
AtCoder Beginner Contest 181 题解的更多相关文章
- AtCoder Beginner Contest 154 题解
人生第一场 AtCoder,纪念一下 话说年后的 AtCoder 比赛怎么这么少啊(大雾 AtCoder Beginner Contest 154 题解 A - Remaining Balls We ...
- AtCoder Beginner Contest 153 题解
目录 AtCoder Beginner Contest 153 题解 A - Serval vs Monster 题意 做法 程序 B - Common Raccoon vs Monster 题意 做 ...
- AtCoder Beginner Contest 177 题解
AtCoder Beginner Contest 177 题解 目录 AtCoder Beginner Contest 177 题解 A - Don't be late B - Substring C ...
- AtCoder Beginner Contest 184 题解
AtCoder Beginner Contest 184 题解 目录 AtCoder Beginner Contest 184 题解 A - Determinant B - Quizzes C - S ...
- AtCoder Beginner Contest 173 题解
AtCoder Beginner Contest 173 题解 目录 AtCoder Beginner Contest 173 题解 A - Payment B - Judge Status Summ ...
- AtCoder Beginner Contest 172 题解
AtCoder Beginner Contest 172 题解 目录 AtCoder Beginner Contest 172 题解 A - Calc B - Minor Change C - Tsu ...
- AtCoder Beginner Contest 169 题解
AtCoder Beginner Contest 169 题解 这场比赛比较简单,证明我没有咕咕咕的时候到了! A - Multiplication 1 没什么好说的,直接读入两个数输出乘积就好了. ...
- AtCoder Beginner Contest 148 题解
目录 AtCoder Beginner Contest 148 题解 前言 A - Round One 题意 做法 程序 B - Strings with the Same Length 题意 做法 ...
- AtCoder Beginner Contest 151 题解报告
总的来说,这次的题目比较水,然而菜菜的我并没有把所有题目都做完,话不多说,直接来干货: A:Next Alphabet 题目链接:https://atcoder.jp/contests/abc151/ ...
随机推荐
- 剑指offer-字符串&数字规律
1. 表示数值的字符串 请实现一个函数用来判断字符串是否表示数值(包括整数和小数).例如,字符串"+100","5e2","-123",&q ...
- osgEarth使用笔记1——显示一个数字地球
目录 1. 概述 2. 实现 2.1. 三维显示 2.2. 二维显示 1. 概述 osgEarth支持.earth格式的文件,里面保存了数字地球相关信息的配置XML,只需要读取这个配置文件,就可以直接 ...
- Win7 64X 安装VisualSVNServer 2.6.0过程中出现Custom action InstallWMISchemaExcute failed: Cannot query proxy blanket: No such interface supported (0x80004002)
Win7 64X 安装VisualSVNServer 2.6.0过程中出现错误:Custom action InstallWMISchemaExcute failed: Cannot query pr ...
- C 清空输入缓冲区,以及fflush(stdin)的使用误区和解决方法
转载:https://blog.csdn.net/Veniversum/article/details/62048870 对C 语言初学者来说,fflush(stdin)函数被解释为会清空输入缓冲区的 ...
- matlab中fopen 打开文件或获得有关打开文件的信息
参考:https://ww2.mathworks.cn/help/matlab/ref/fopen.html?searchHighlight=fopen&s_tid=doc_srchtitle ...
- 踩坑系列:MySql only_full_group_by配置,竟导致所有应用报错?
1. 踩坑经历 一个很平常的下午,大家都在埋头认真写bug呢,突然企业微信群里炸锅了,好多应用都出现大量的Error日志,而且都报同一个错误,就是下面这个: Caused by: com.mysql. ...
- Java源码详解系列(十一)--Spring的使用和源码
Spring 是一个一站式的 Java 框架,致力于提高我们项目开发的效率.通过 Spring,我们可以避免编写大量额外代码,更专注于我们的核心逻辑.目前,Spring 已经成为最受欢迎的 Java ...
- c#之task与thread区别及其使用
如果需要查看更多文章,请微信搜索公众号 csharp编程大全,需要进C#交流群群请加微信z438679770,备注进群, 我邀请你进群! ! ! --------------------------- ...
- ansible-playbook简介
1. ansible-playbook简介 • Playbooks 与 adhoc 相比,是一种完全不同的运用 ansible 的方式,是非常之强大的. • 简单来说,playbooks 是一种简单的 ...
- 如何把base64格式的图片上传到到阿里云oss c#版
今天碰到需要把canvas上的的图片转存到阿里云oss,于是百度了半天,一个能打的答案都没有.怒了,自己搞起. 代码超级简单,需要先引入nuget 中啊里云的oss api 1 byte[] arr ...