021中国大学生程序设计竞赛(CCPC)- 压力测试赛题解
A.Matrix
挺狗的一道题,从开始冲到最后都没冲出来,都没啥思路。
其实分开考虑每个数的贡献,这个想法也存在过,就是不知道该怎么计算,我们考虑我们单独考虑一个数字\(i(1\leq i\leq n)\)的贡献,其实就是在有一行答案是\(i\)的情况下总的方案数有多少个。同时我们注意到,每个不同的数之间是互不冲突的,因为在一个方案中,我们也是每行求每个数的答案然后累加起来。所以我们只考虑一个数在多少个不同的方案里贡献了答案。首先我们要选一行,其次保证这一行的答案是\(i\),考虑到这一行的其他数必须都比它大,也就是\(C_{n^2-i}^{n-1}\)个,其次考虑这一行\(n\)个数的排列,就是\(n!\),还有就是除了这一行,其他所有数的排列。就是\((n^2-n)!\)也就是说单独一个\(i\)的贡献就是\(n*C_{n^2-i}^{n-1}*n!*(n^2-n)!\)所有数的答案就是\(ans=n*n!*(n^2-n)!\sum_{i=1}^{n}C_{n^2-i}^{n-1}\)数据\(n=5000\),随便都可以过。
//不等,不问,不犹豫,不回头.
#include<bits/stdc++.h>
#define _ 0
#define ls p<<1
#define db double
#define rs p<<1|1
#define P 998244353
#define ll long long
#define INF 1000000000
#define get(x) x=read()
#define PLI pair<ll,int>
#define PII pair<int,int>
#define ull unsigned long long
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(x,y,z) for(int x=y;x<=z;++x)
#define fep(x,y,z) for(int x=y;x>=z;--x)
#define go(x) for(int i=link[x],y=a[i].y;i;y=a[i=a[i].next].y)
using namespace std;
const int N=5005;
ll jc[N*N];
inline int read()
{
int x=0,ff=1;
char ch=getchar();
while(!isdigit(ch)) {if(ch=='-') ff=-1;ch=getchar();}
while(isdigit(ch)) {x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*ff;
}
inline ll power(ll x,int y)
{
ll ans=1;
while(y)
{
if(y&1) ans=ans*x%P;
y>>=1;
x=x*x%P;
}
return ans%P;
}
inline void prework()
{
jc[0]=1;
rep(i,1,25000000) jc[i]=jc[i-1]*i%P;
}
inline ll C(int n,int m) {return jc[n]*power(jc[m],P-2)%P*power(jc[n-m],P-2)%P;}
int main()
{
//freopen("1.in","r",stdin);
prework();
int get(T);
while(T--)
{
int get(n);
ll ans=n;
ans=ans*jc[n]%P*jc[n*n-n]%P;
ll p=0;
rep(i,1,n) p=(p+C(n*n-i,n-1))%P;
putl(ans*p%P);
}
return (0^_^0);
}
//以吾之血,铸吾最后的亡魂.
B.Cypher
关于机关解密的大模拟题....看懂题意谁都会做....
//不等,不问,不犹豫,不回头.
#include<bits/stdc++.h>
#define _ 0
#define ls p<<1
#define db double
#define rs p<<1|1
#define P 1000000007
#define ll long long
#define INF 1000000000
#define get(x) x=read()
#define PLI pair<ll,int>
#define PII pair<int,int>
#define ull unsigned long long
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(x,y,z) for(int x=y;x<=z;++x)
#define fep(x,y,z) for(int x=y;x>=z;--x)
#define go(x) for(int i=link[x],y=a[i].y;i;y=a[i=a[i].next].y)
using namespace std;
const int N=60;
int p,n,cnt[N],Q;
char id[N],pan[N][3][N],c[N],fan[N],sr[N];
inline int read()
{
int x=0,ff=1;
char ch=getchar();
while(!isdigit(ch)) {if(ch=='-') ff=-1;ch=getchar();}
while(isdigit(ch)) {x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*ff;
}
inline void roll(int id)
{
char c=pan[id][1][0];
rep(i,0,24) pan[id][1][i]=pan[id][1][i+1];
pan[id][1][25]=c;
c=pan[id][2][0];
rep(i,0,24) pan[id][2][i]=pan[id][2][i+1];
pan[id][2][25]=c;
}
inline char solve(char o)
{
int now=1;
while(1)
{
roll(now);
cnt[now]++;
if(cnt[now]%26!=0) break;
now++;
}
int Id=(int)id[o-'A']-'A';
rep(i,1,n)
{
char c=pan[i][1][Id];
rep(j,0,25) if(pan[i][2][j]==c) {Id=j;break;}
}
rep(i,0,25) if(fan[i]-'A'==Id) {Id=i;break;}
fep(i,n,1)
{
char c=pan[i][2][Id];
rep(j,0,25) if(pan[i][1][j]==c) {Id=j;break;}
}
return id[Id];
}
int main()
{
//freopen("1.in","r",stdin);
int get(T);
while(T--)
{
get(p);
rep(i,0,25) id[i]='A'+i;
rep(i,1,p)
{
scanf("%s",sr+1);
swap(id[sr[1]-'A'],id[sr[2]-'A']);
}
get(n);
rep(i,1,n)
{
rep(j,0,25) pan[i][1][j]='A'+j;
}
rep(i,1,n) scanf("%s",pan[i][2]);
memset(cnt,0,sizeof(cnt));
rep(i,1,n)
{
int get(x);
cnt[i]+=x;
rep(j,1,cnt[i])
{
roll(i);
if(cnt[i]%26==0&&i!=n) roll(i+1),cnt[i+1]++;
}
}
scanf("%s",fan);
get(Q);
rep(i,1,Q)
{
scanf("%s",sr+1);
int m=strlen(sr+1);
rep(j,1,m) printf("%c",solve(sr[j]));
puts("");
}
}
return (0^_^0);
}
//以吾之血,铸吾最后的亡魂.
C.Vertex Deletion
关于删点的问题,关于这个题,当时也想到了可能要用到树形\(dp\)去解决,也想到了要设\(f[x][0/1]\)来表示清楚当前这个点删不删的方案数,可还是想不太清楚,就弃了。
首先第一个是设状态的问题,我们先考虑我们随便切之后可能会有哪些状态,从根节点往下看,以当前点\(x\)为例,无外乎就三种状态:\(x\)被删掉,\(x\)被保留且只有\(x\)单独的一个点(即\(x\)不与其他点相连),\(x\)被保留且至少还连着其他的一个点。既然有三种状态,那我们设状态时就可以先这样设着\(f[x][0/1/2]\),没有用的时候再剔除也行。那么考虑\(dfs\)的时候,状态如何转移,注意我们定义的状态是以当前点\(x\)为根的子树中,\(x\)处于以上状态时的合法方案数。
那么当\(x\)被删除时,其各个儿子被相互独立那么儿子只能选择连着其儿子来保持方案合法或者选择删除自己。则\(f[x][0]=\prod (f[y][2]+f[y][0])\)。
当\(x\)被保留且单独一个点时,那么儿子必须全部删去,否则就会使得\(x\)与\(y\)相连。即\(f[x][1]=\prod f[y][0]\)
当\(x\)被保留且至少连一个点时,这个方案有点多,我们只要和任意一个儿子相连即可。如果正着求不太行的话,我们考虑容斥,每个儿子有两种选择,要么保留,要么删除,而其中保留还可以选择至少连一个点和删除,这样的话我们直接将所有儿子的两种选择都选上即\(f[x][1]=\prod (f[y][1]+f[y][0]+f[y][2])\)可这样的话发现当所有儿子选择删除时,我们当前的状态就不合法了,但只有这一种情况下才不合法我们直接从总方案中减去即可,而发现这种方案恰好就是\(f[x][1]\)。即\(f[x][1]=\prod (f[y][1]+f[y][0]+f[y][2])-f[x][1]\)。那么最后的答案就是\(f[1][0]+f[1][2]\).
//不等,不问,不犹豫,不回头.
#include<bits/stdc++.h>
#define _ 0
#define ls p<<1
#define db double
#define rs p<<1|1
#define P 998244353
#define ll long long
#define INF 1000000000
#define get(x) x=read()
#define PLI pair<ll,int>
#define PII pair<int,int>
#define ull unsigned long long
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(x,y,z) for(int x=y;x<=z;++x)
#define fep(x,y,z) for(int x=y;x>=z;--x)
#define go(x) for(int i=link[x],y=a[i].y;i;y=a[i=a[i].next].y)
using namespace std;
const int N=1e5+10;
ll f[N][3],n;
vector<int>son[N];
inline int read()
{
int x=0,ff=1;
char ch=getchar();
while(!isdigit(ch)) {if(ch=='-') ff=-1;ch=getchar();}
while(isdigit(ch)) {x=(x<<1)+(x<<3)+(ch^48);ch=getchar();}
return x*ff;
}
inline void dfs(int x,int fa)
{
f[x][0]=f[x][1]=f[x][2]=1;
for(auto y:son[x])
{
if(y==fa) continue;
dfs(y,x);
f[x][0]=(f[x][0]*(f[y][2]+f[y][0]))%P;
f[x][1]=(f[x][1]*f[y][0])%P;
f[x][2]=(f[x][2]*(f[y][0]+f[y][1]+f[y][2]))%P;
}
f[x][2]=(f[x][2]-f[x][1]+P)%P;
}
int main()
{
//freopen("1.in","r",stdin);
int get(T);
while(T--)
{
get(n);
rep(i,1,n) son[i].clear();
rep(i,1,n-1)
{
int get(x),get(y);
son[x].push_back(y);
son[y].push_back(x);
}
dfs(1,0);
putl((f[1][0]+f[1][2])%P);
}
return (0^_^0);
}
//以吾之血,铸吾最后的亡魂.
D.Lowbit
这个题还是挺好的,发现包括上一次的相乘,这一类题都有一个比较重要的性质,就是某些操作在操作一定次数之后就会出现一些神奇的变化或者不可能成为答案。这个题就是一样的,你会发现这个题每个数在进行一定次数的增加\(lowbit\)之后,等到这个数二进制下只剩一个\(1\)的时候,再加\(lowbit\)就变成乘\(2\)了,而乘\(2\)这个操作我们很容易维护,所以直接写一个线段树,维护一下每个数是不是到达这个状态了即可。
021中国大学生程序设计竞赛(CCPC)- 压力测试赛题解的更多相关文章
- HDU6237-A Simple Stone Game-找素因子(欧拉函数)-2017中国大学生程序设计竞赛-哈尔滨站-重现赛
A Simple Stone Game Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Ot ...
- HDU6235-Permutation-水题-2017中国大学生程序设计竞赛-哈尔滨站-重现赛
Permutation Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others)Tot ...
- HDU 6237.A Simple Stone Game-欧拉函数找素因子 (2017中国大学生程序设计竞赛-哈尔滨站-重现赛)
A Simple Stone Game Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Ot ...
- HDU 6235.Permutation (2017中国大学生程序设计竞赛-哈尔滨站-重现赛)
Permutation Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others)Tot ...
- HDU 6273.Master of GCD-差分数组 (2017中国大学生程序设计竞赛-杭州站-重现赛(感谢浙江理工))
Super-palindrome 题面地址:http://acm.hdu.edu.cn/downloads/CCPC2018-Hangzhou-ProblemSet.pdf 这道题是差分数组的题目,线 ...
- [BFS,A*,k短路径] 2019中国大学生程序设计竞赛(CCPC) - 网络选拔赛 path (Problem - 6705)
题目:http://acm.hdu.edu.cn/showproblem.php?pid=6705 path Time Limit: 2000/2000 MS (Java/Others) Mem ...
- [贪心,dp] 2019中国大学生程序设计竞赛(CCPC) - 网络选拔赛 Fishing Master (Problem - 6709)
题目:http://acm.hdu.edu.cn/showproblem.php?pid=6709 Fishing Master Time Limit: 2000/1000 MS (Java/Othe ...
- 2019中国大学生程序设计竞赛(CCPC) - 网络选拔赛(8/11)
$$2019中国大学生程序设计竞赛(CCPC)\ -\ 网络选拔赛$$ \(A.\hat{} \& \hat{}\) 签到,只把AB都有的位给异或掉 //#pragma comment(lin ...
- 2016中国大学生程序设计竞赛 - 网络选拔赛 C. Magic boy Bi Luo with his excited tree
Magic boy Bi Luo with his excited tree Problem Description Bi Luo is a magic boy, he also has a migi ...
随机推荐
- 学习PHP中Fileinfo扩展的使用
今天来学习的这个扩展其实现在也已经是标配的一个扩展了,为什么呢?因为 Laravel 框架在安装的时候它就是必须的一个扩展,没有打开它的话,连 Laravel 框架都是无法使用的. Fileinfo ...
- PHP中的PDO操作学习(四)查询结构集
关于 PDO 的最后一篇文章,我们就以查询结果集的操作为结束.在数据库的操作中,查询往往占的比例非常高.在日常的开发中,大部分的业务都是读多写少型的业务,所以掌握好查询相关的操作是我们学习的重要内容. ...
- 【转载】在Windows终端中显示UTF-8字符
一直苦恼于如何在Windows终端中显示UTF-8字符的问题.比如,在MySQL命令行下,如果数据库的编码是UTF-8,那么,在查询数据库的时候,里面的中文都会变成乱码.今天半无意的搜索了一下,结果发 ...
- english note(6.10to6.16)
6.10 http://www.51voa.com/VOA_Special_English/blackbeard-s-ship-comes-to-the-us-supreme-court-82217_ ...
- Windows下Vim插件管理器Vundle的安装以及使用简介
Vundle下载 从GitHub clone仓库 cd %USERPROFILE% git clone git@github.com:VundleVim/Vundle.vim.git %USERPRO ...
- IDEA远程部署调试Java应用程序
IDEA远程部署调试Java应用程序 目录 IDEA远程部署调试Java应用程序 基本概述 准备工作 远程服务器准备 安装JDK 配置JAVA_HOME 项目准备 创建一个SpringBoot项目 创 ...
- MySQL学习总结:提问式回顾 undo log 相关知识
原文链接:MySQL学习总结:提问式回顾 undo log 相关知识 1.redo 日志支持恢复重做,那么如果是回滚事务中的操作呢,也会有什么日志支持么? 也回滚已有操作,那么就是想撤销,对应的有撤销 ...
- Jetpack Compose学习(7)——MD样式架构组件Scaffold及导航底部菜单
Jetpack Compose学习(7)--MD样式架构组件Scaffold及导航底部菜单 | Stars-One的杂货小窝 Compose给我们提供了一个Material Design样式的首页组件 ...
- js 手动实现 promise.all的功能
在中高级面试中,实现一个promise.all是一个频率较高的面试题 首先分析下 promise.all(),(参考MDN) 接收一个promise的iterable类型(注:Array,Map,Se ...
- 每日总结:Number&Math类(2021.10.4)
Java语言为每一个内置数据类型提供了对应的包装类. 所有的包装类(Integer.Long.Byte.Double.Float.Short)都是抽象类Number的子类 其中Integer 对应的基 ...