【超好懂的比赛题解】The 2021 CCPC Weihai Onsite

2023-11-05 06:32

本文主要是介绍【超好懂的比赛题解】The 2021 CCPC Weihai Onsite,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!


title :The 2021 CCPC Weihai Onsite
date : 2021-12-1
tags : ACM,练习记录
author : Linno


题目链接 :https://codeforces.com/gym/103428

补题进度 :5/13

A. Goodbye, Ziyin!

题意

给一颗树,求能够作为二叉树的根的节点数。

思路

签到题。把每个点度数记录下来,对每个结点的度数,小于等于2则满足;大于3的时候答案为0。

代码

#include<bits/stdc++.h>
#define inf 0x3f3f3f3f
#define int long long
using namespace std;
const int N=1e6+7;
const int mod=1e9+7;vector<int>G[N];
int n,u,v,deg[N],ans=0;signed main(){ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);cin>>n;for(int i=1;i<n;i++){cin>>u>>v;G[u].push_back(v);G[v].push_back(u);deg[u]++;deg[v]++;}for(int i=1;i<=n;i++){if(deg[i]>3){ans=0;break;}if(deg[i]<=2) ans++;}cout<<ans<<"\n"; return 0;
}

D. Period

题意

给定字符串和q个询问,每次询问把一个位置修改成‘#’,求周期的数量。

思路

签到题,先预处理出原来的周期,然后对每次询问二分出满足条件的周期即可。

代码

#include<bits/stdc++.h>
using namespace std;
const int maxn=1e6+5;int pi[maxn],v1[maxn],v2[maxn],n,q,u,minv,t1,t2;
string s;int main()
{ios::sync_with_stdio(false);cin.tie(0); cout.tie(0);cin>>s>>q; n=s.length();for(int i=1;i<n;i++){int j=pi[i-1];while(j&&s[i]!=s[j])j=pi[j-1];if(s[i]==s[j])j++;pi[i]=j;}if(pi[n-1])minv=pi[n-1],v1[++t1]=minv,v2[++t2]=minv;while(minv&&pi[minv-1]){minv=pi[minv-1];v1[++t1]=minv;v2[++t2]=minv;}for(int i=1;i<=t1;i++)v1[i]=n-v1[i]+1;reverse(v2+1,v2+1+t2); for(int i=1;i<=q;i++){cin>>u; int p1=upper_bound(v1+1,v1+1+t1,u)-v1;int p2=lower_bound(v2+1,v2+1+t2,u)-v2;cout<<min(t1-p1+1,p2-1)<<"\n";}return 0;
}

G.Desserts

题意

有n种糖果,每种ai个,分给k只队伍,要求每个队伍不能重复拿相同的糖果并且要分完。求1到m每个k的方案数。

思路

结论很简单,就是把每只队分给每种糖果的组合数的结果累乘。 a n s k = Π i = 1 n C ( k , a i ) ans_k=\Pi_{i=1}^nC(k,a_i) ansk=Πi=1nC(k,ai)

O ( n ∗ m ) O(n*m) O(nm)是会超时的,要再注意每种糖果总和不超过1e5这个条件,说明不同的ai只有根号种,相同种的糖果不需要重复计算,用快速幂的形势就可以把复杂度降为 O ( m ∑ a l o g n ) O(m\sqrt{\sum a} logn) O(ma logn)

代码

#include<bits/stdc++.h>
#define int long long 
using namespace std;
const int N=1e5+100;
const int mod=998244353;int a[N],kinds[N],ans,n,m,mx=0;
int fac[N],inv[N],finv[N];
int vt[N],cnt=0;int fpow(int a,int b){int res=1;while(b){if(b&1)res=res*a%mod;a=a*a%mod;b>>=1;} return res;
}void init(){memset(kinds,0,sizeof(kinds));fac[0]=inv[0]=inv[1]=finv[0]=finv[1]=1ll;for(int i=1;i<N;i++)fac[i]=fac[i-1]*i%mod;for(int i=2;i<N;i++)inv[i]=(mod-mod/i)*inv[mod%i]%mod;for(int i=2;i<N;i++)finv[i]=finv[i-1]*inv[i]%mod;
}inline int C(int a,int b){if(b>a)return 0;else return fac[a]*finv[a-b]%mod*finv[b]%mod;
}signed main(){ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);cin>>n>>m;init();for(int i=1;i<=n;i++){cin>>a[i];kinds[a[i]]++;mx=max(a[i],mx);}for(int i=1;i<=mx;i++){if(kinds[i]) vt[++cnt]=i;}for(int k=1;k<=m;k++){ans=1ll;for(int i=1;i<=cnt;i++){ans=ans*fpow(C(k,vt[i]),kinds[vt[i]])%mod;ans%=mod;}cout<<ans<<"\n";}return 0;
}

H. city safety

题意

n个城市,连成一棵树,每个城市的花费为wi。并且有收益表pi。如果修复i城市时,所有已花费城市距离该城市不超过pi,那么可获得pi的收益(取最大的一个)。问最大收益。

思路

看了题解,是用最小割来做,暂时还不会这东西。

代码

还写不出来,待补。

J. Circular Billiard Table

题意

在圆形球桌上给一个入射角,问要反射几次才能回到起点。

思路

签到题。假设球碰撞了n次,转了k圈回到原点。那么 2 n ∗ a b = 360 ∗ k 2n*\frac{a}{b}=360*k 2nba=360k,稍微化简得 n ∗ a = 180 ∗ k ∗ b n*a=180*k*b na=180kb,那么可以构造 k = a , n = 180 ∗ b k=a,n=180*b k=a,n=180b,使得等式必定成立,然后取k和n的gcd即可。

代码

#include<bits/stdc++.h>
#define inf 0x3f3f3f3f
#define int long long
using namespace std;
const int N=2e5+7;
const int mod=1e9+7;int gcd(int a,int b){return b?gcd(b,a%b):a;}int t,a,b,n,k,d;signed main(){//ios::sync_with_stdio(0);//cin.tie(0);cout.tie(0);cin>>t;while(t--){cin>>a>>b;n=180*b; //碰撞次数 k=a; //圈数d=gcd(n,k);while(d!=1){n/=d;k/=d;d=gcd(n,k);}cout<<n-1<<"\n";}return 0;
}

M. 810975

题意

给一个n,m,k,构造一个n位的01串,其中有m个1并且最长的连续的1长度为k。

思路

多项式容易写炸,考虑用组合数学的方法。设 f ( n , m , k ) f(n,m,k) f(n,m,k)是长度为n且有m个1的字符串,每段长度不大于k,那么答案转化为 f ( n , m , k ) − f ( n , m , k − 1 ) f(n,m,k)-f(n,m,k-1) f(n,m,k)f(n,m,k1),可以用容斥来做。用隔板法我们可以转化为把m个1放到n-m+1个盒子(0是隔板)里。然后这里由于我经验不足直接递归写炸了,借鉴了一个很妙的公式来进一步容斥。

for(int i=0;i<=p;i++){ //枚举每一段 int op=i&1?-1:1;res+=op*C(p,i)*C(m-i*(k+1)+p-1,p-1)%mod;
//感觉很妙,p段选i段来装最长的,并且容斥掉了剩下长度大于k的方案 
}

因为还不太理解,可能注释得不好,如果有更详细的理解可以告诉我。

代码

#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N=2e5+7;
const int mod=998244353;int fact[N],inv[N];void init(){ //预处理 fact[0]=inv[0]=inv[1]=1;for(int i=1;i<N;i++) fact[i]=fact[i-1]*i%mod;for(int i=2;i<N;i++) inv[i]=(mod-mod/i)*inv[mod%i]%mod;for(int i=2;i<N;i++) inv[i]=inv[i]*inv[i-1]%mod;
}int C(int n,int m){ //O(1)求组合数 if(m>n||m<0) return 0;return fact[n]*inv[m]%mod*inv[n-m]%mod;
}inline int f(int n,int m,int k){ if(!k){ if(!m) return 1; //没有1 else return 0;}if(k>m) return 0; //不可能存在k比1总数大的情况 int res=0,p=n-m+1; //隔板拆成p段 for(int i=0;i<=p;i++){ //枚举每一段 int op=i&1?-1:1;res+=op*C(p,i)*C(m-i*(k+1)+p-1,p-1)%mod;//感觉很妙,p段选i段来装最长的,并且容斥掉了剩下长度大于k的方案 }return (res+mod)%mod;
}inline int fc(int n,int m,int k){  //容斥 return (f(n,m,k)-f(n,m,k-1)+mod)%mod;
}signed main(){int n,m,k;cin>>n>>m>>k;init();if(!k||k>m) cout<<f(n,m,k)<<"\n";else cout<<fc(n,m,k)<<"\n"return 0;
}

这篇关于【超好懂的比赛题解】The 2021 CCPC Weihai Onsite的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



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

相关文章

C++ | Leetcode C++题解之第393题UTF-8编码验证

题目: 题解: class Solution {public:static const int MASK1 = 1 << 7;static const int MASK2 = (1 << 7) + (1 << 6);bool isValid(int num) {return (num & MASK2) == MASK1;}int getBytes(int num) {if ((num &

C语言 | Leetcode C语言题解之第393题UTF-8编码验证

题目: 题解: static const int MASK1 = 1 << 7;static const int MASK2 = (1 << 7) + (1 << 6);bool isValid(int num) {return (num & MASK2) == MASK1;}int getBytes(int num) {if ((num & MASK1) == 0) {return

C - Word Ladder题解

C - Word Ladder 题解 解题思路: 先输入两个字符串S 和t 然后在S和T中寻找有多少个字符不同的个数(也就是需要变换多少次) 开始替换时: tips: 字符串下标以0开始 我们定义两个变量a和b,用于记录当前遍历到的字符 首先是判断:如果这时a已经==b了,那么就跳过,不用管; 如果a大于b的话:那么我们就让s中的第i项替换成b,接着就直接输出S就行了。 这样

【秋招笔试】9.07米哈游秋招改编题-三语言题解

🍭 大家好这里是 春秋招笔试突围,一起备战大厂笔试 💻 ACM金牌团队🏅️ | 多次AK大厂笔试 | 大厂实习经历 ✨ 本系列打算持续跟新 春秋招笔试题 👏 感谢大家的订阅➕ 和 喜欢💗 和 手里的小花花🌸 ✨ 笔试合集传送们 -> 🧷春秋招笔试合集 🍒 本专栏已收集 100+ 套笔试题,笔试真题 会在第一时间跟新 🍄 题面描述等均已改编,如果和你笔试题看到的题面描述

LeetCode 第414场周赛个人题解

目录 Q1. 将日期转换为二进制表示 原题链接 思路分析 AC代码 Q2. 范围内整数的最大得分 原题链接 思路分析 AC代码 Q3. 到达数组末尾的最大得分 原题链接 思路分析 AC代码 Q4. 吃掉所有兵需要的最多移动次数 原题链接 思路分析 AC代码 Q1. 将日期转换为二进制表示 原题链接 Q1. 将日期转换为二进制表示 思路分析

GPU 计算 CMPS224 2021 学习笔记 02

并行类型 (1)任务并行 (2)数据并行 CPU & GPU CPU和GPU拥有相互独立的内存空间,需要在两者之间相互传输数据。 (1)分配GPU内存 (2)将CPU上的数据复制到GPU上 (3)在GPU上对数据进行计算操作 (4)将计算结果从GPU复制到CPU上 (5)释放GPU内存 CUDA内存管理API (1)分配内存 cudaErro

2021-8-14 react笔记-2 创建组件 基本用法

1、目录解析 public中的index.html为入口文件 src目录中文件很乱,先整理文件夹。 新建components 放组件 新建assets放资源   ->/images      ->/css 把乱的文件放进去  修改App.js 根组件和index.js入口文件中的引入路径 2、新建组件 在components文件夹中新建[Name].js文件 //组件名首字母大写

2021-08-14 react笔记-1 安装、环境搭建、创建项目

1、环境 1、安装nodejs 2.安装react脚手架工具 //  cnpm install -g create-react-app 全局安装 2、创建项目 create-react-app [项目名称] 3、运行项目 npm strat  //cd到项目文件夹    进入这个页面  代表运行成功  4、打包 npm run build

牛客小白月赛100部分题解

比赛地址:牛客小白月赛100_ACM/NOI/CSP/CCPC/ICPC算法编程高难度练习赛_牛客竞赛OJ A.ACM中的A题 #include<bits/stdc++.h>using namespace std;#define ll long long#define ull = unsigned long longvoid solve() {ll a,b,c;cin>>a>>b>

[SWPUCTF 2021 新生赛]web方向(一到六题) 解题思路,实操解析,解题软件使用,解题方法教程

题目来源 NSSCTF | 在线CTF平台因为热爱,所以长远!NSSCTF平台秉承着开放、自由、共享的精神,欢迎每一个CTFer使用。https://www.nssctf.cn/problem   [SWPUCTF 2021 新生赛]gift_F12 这个题目简单打开后是一个网页  我们一般按F12或者是右键查看源代码。接着我们点击ctrl+f后快速查找,根据题目给的格式我们搜索c