NOIp2018集训test-10-4/test-10-5 (联考四day1/day2)
这个day1稍微有点毒瘤吧??
DAY1
排列
以前总是把day1t1想太复杂了翻车,差不多往正解的方向想了一下感觉不可能这么复杂这可是noipday1t1啊一定有非常简单的方法然后翻车了??
题目转换为求二分图完全匹配数,这个怎么都是十分不好算的,容易想到容斥。
用g[i]表示起码选了i条二分图的补图中的边的匹配数。
那么答案就是
$ans=\sum_{i=0}^{n}g[i]*(n-i)!*(-1)^i$
发现这个二分图的补图长得十分有特点啊。
这是若干条不想交的链构成的图,链与链之间互不影响可以单独考虑。用f[i][j][0/1]表示选到某条链上第i个点,在这条链上选了j条边,第i个点有没有被选的方案数,可以分别dp出每条链。
再跑个背包合并所有链,容斥统计答案即可。这样就有95分啦。
//Achen
#include<bits/stdc++.h>
#define For(i,a,b) for(int i=(a);i<=(b);i++)
#define Rep(i,a,b) for(int i=(a);i>=(b);i--)
#define Formylove return 0
const int N=,p=;
using namespace std;
typedef long long LL;
typedef double db;
int n,K,g[N],f[N][N][],fac[N],up; template<typename T>void read(T &x) {
T f=; x=; char ch=getchar();
while(ch!='-'&&(ch<''||ch>'')) ch=getchar();
if(ch=='-') f=-,ch=getchar();
for(;ch>=''&&ch<='';ch=getchar()) x=x*+ch-''; x*=f;
} int mo(LL x) { return x%p; } #define ANS
int main() {
#ifdef ANS
freopen("permutation.in","r",stdin);
freopen("permutation.out","w",stdout);
#endif
read(n); read(K);
fac[]=;
For(i,,n) fac[i]=(LL)fac[i-]*i%p;
g[]=;
For(cs,,) {
For(i,,K) {
f[i][][]=;
int j=i,tp=;
for(;;) {
if(j+K>n) break;
j+=K; tp++;
For(l,,tp) {
f[j][l+][]=f[j-K][l][];
f[j][l][]=(f[j-K][l][]+f[j-K][l][])%p;
}
}
Rep(l,up,) For(m,,tp)
(g[l+m]+=(LL)g[l]*(f[j][m][]+f[j][m][])%p)%=p;
up+=tp;
}
}
LL ans=;
For(i,,n) {
//printf("%d\n",g[i]);
if(!(i&)) ans=(ans+(LL)g[i]*fac[n-i]%p)%p;
else ans=(ans-(LL)g[i]*fac[n-i]%p+p)%p;
}
printf("%lld\n",ans);
//cerr<<clock()<<endl;
Formylove;
}
95pt
最后5分是什么玩意???
发现这些链其实都一样,只有两种不同长度。又发现刚才的dp其实是一个组合数。就可以直接得到最后要的f,然后多项式exp就可以的答案了。noip之前我不会写这种玩意的。。
苹果树
最简单的一道题,很多人都切了,而且各种方法花样AC。大致有标解的lca,辉神李巨的树剖,ljq的伪tarjan。但是我的随机化应该是最好写的,写得快点大概5min就够了吧。
//Achen
#include<bits/stdc++.h>
#define For(i,a,b) for(int i=(a);i<=(b);i++)
#define Rep(i,a,b) for(int i=(a);i>=(b);i--)
#define Formylove return 0
const int N=;
using namespace std;
typedef unsigned long long LL;
typedef double db;
int n,m; template<typename T>void read(T &x) {
T f=; x=; char ch=getchar();
while(ch!='-'&&(ch<''||ch>'')) ch=getchar();
if(ch=='-') f=-,ch=getchar();
for(;ch>=''&&ch<='';ch=getchar()) x=x*+ch-''; x*=f;
} int ecnt,fir[N],nxt[N<<],to[N<<];
void add(int u,int v) {
nxt[++ecnt]=fir[u]; fir[u]=ecnt; to[ecnt]=v;
nxt[++ecnt]=fir[v]; fir[v]=ecnt; to[ecnt]=u;
} map<LL,int>mp,mp2;
LL val[N],val2[N],ans;
void dfs(int x,int fa) {
for(int i=fir[x];i;i=nxt[i]) if(to[i]!=fa) {
dfs(to[i],x);
val[x]=(val[x]^val[to[i]]);
}
if(fa) {
if(!val[x])
ans+=m;
else if(mp[val[x]])
ans++;
}
} #define ANS
int main() {
#ifdef ANS
freopen("tree.in","r",stdin);
freopen("tree.out","w",stdout);
#endif
srand();
read(n); read(m);
For(i,,n) {
int u,v;
read(u); read(v);
add(u,v);
}
For(i,,m) {
int u,v;
read(u); read(v);
LL t;
t=(((LL)rand()<<)|rand());
while(!t) {
t=(((LL)rand()<<)|rand());
}
mp[t]=;
val[u]^=t;
val[v]^=t;
}
dfs(,);
printf("%llu\n",ans);
//cerr<<clock()<<endl;
Formylove;
}
多项式
披着斗地主外皮的多项式??瑟瑟发抖。
模拟只给50,我大概写模拟都要写3h+把。。。写了个30分的暴力还写挂了,没把不同花色的同种对子区分开。。。
还是noip之前不改系列。
//Achen
#include<bits/stdc++.h>
#define For(i,a,b) for(int i=(a);i<=(b);i++)
#define Rep(i,a,b) for(int i=(a);i>=(b);i--)
#define Formylove return 0
const int N=,p=;
using namespace std;
typedef long long LL;
typedef double db;
int T,n,cnt[N],cc[N],C[][],pr[];
LL ans;
char s[N]; template<typename T>void read(T &x) {
T f=; x=; char ch=getchar();
while(ch!='-'&&(ch<''||ch>'')) ch=getchar();
if(ch=='-') f=-,ch=getchar();
for(;ch>=''&&ch<='';ch=getchar()) x=x*+ch-''; x*=f;
} void solve1() {
ans=;
For(i,,) cc[i]=;
For(i,,) cc[cnt[i]]++;
if(n==) ans=;
else if(n==) {
if(cc[]==) ans=;
else ans=;
}
else if(n==) {
if(cc[]==) ans=;
else if(cc[]==) ans=;
else ans=;
}
else if(n==) {
ans++; //4 single
if(cc[]==) ans+=; //4:1 3+1:C(4,3) 2+2:3 2+1+1:C(4,2)
if(cc[]==) ans+=; //3+1 3+1 2+1+1:C(3,2)
if(cc[]==) ans++; //2+1
else if(cc[]==) ans+=; //2+2 2+1+1 2+1+1
}
} void dfs2(int pos,int num,int lim) {
if(pos==) {
ans=(ans+num)%p;
return;
}
//if(cnt[pos]==2) dfs2(pos+1,num*2%p,0); // 1+1 or 2
//else dfs2(pos+1,num,0); //
if(cnt[pos]==) dfs2(pos+,num,); for(int j=pos+;cnt[j]&&j<=;j++) { //shun zi
if(j>=pos+&&j>lim) {
int N=num;
For(k,pos,j) {
N=(LL)N*C[cnt[k]][]%p;
cnt[k]--;
}
dfs2(pos,N,j);
For(k,pos,j) cnt[k]++;
}
}
for(int j=pos;cnt[j]==&&j<=;j++) { //lian dui
if(j>=pos+) {
dfs2(j+,num,);
}
}
} #define ANS
int main() {
#ifdef ANS
freopen("polynomial.in","r",stdin);
//freopen("polynomial.out","w",stdout);
#endif
read(T);
For(i,,) C[i][]=;
pr[]=;
For(i,,) pr[i]=pr[i-]*%p;
For(i,,) For(j,,i) C[i][j]=(C[i-][j-]+C[i-][j])%p;
while(T--) {
read(n);
memset(cnt,,sizeof(cnt));
For(i,,n) {
scanf("%s",s);
int len=strlen(s);
if(len==) {
if(s[]=='J') cnt[]++;
else if(s[]=='Q') cnt[]++;
else if(s[]=='K') cnt[]++;
else if(s[]=='A') cnt[]++;
else {
if(s[]-''==) cnt[]++;
else cnt[s[]-'']++;
}
}
else {
if(s[]=='') cnt[]++;
else cnt[]++;
}
}
For(i,,n) scanf("%s",s);
ans=;
if(n<=) solve1();
else dfs2(,,);
printf("%lld\n",ans);
}
//cerr<<clock()<<endl;
Formylove;
}
30pt
DAY2
day2其实并不难,应该是容易AK的,但是DCOI实在太菜了。。
我写t2的时候把线段树的时空复杂度算错了,就想写分块水水,码力太弱(本质是没想清楚),花了太多时间最终却没调出来,只交了暴力,还导致本来很简单的t3根本没时间思考,写了暴力就交。
序列
这种玩意套路的做法就是枚举每个起点i,然后分别统计后面a[j]-(j-i+1)大于0的和小于0的和,前面类似。
也就是每个位置的权值是a[i]-i,每次查询大于或小于某个权值的数的权值和。
树状数组肯定是可以做的,常数优秀一点说不定能过呢。
发现起点一位一位的移时,每次查询的那个数是一点点增大或减小的,而ai又很小,拿cnt数组记一下,每次把刚刚越过线的部分算一算就可以On做了。
//Achen
#include<bits/stdc++.h>
#define For(i,a,b) for(int i=(a);i<=(b);i++)
#define Rep(i,a,b) for(int i=(a);i>=(b);i--)
#define Formylove return 0
const int N=4e6+;
typedef long long LL;
typedef double db;
using namespace std;
LL n,a[N],cnt[N],pos;
LL ans[N],now,sum,sumcnt,nowcnt; template<typename T>void read(T &x) {
char ch=getchar(); T f=; x=;
while(ch!='-'&&(ch<''||ch>'')) ch=getchar();
if(ch=='-') f=-,ch=getchar();
for(;ch>=''&&ch<='';ch=getchar()) x=x*+ch-''; x*=f;
} #define ANS
int main() {
#ifdef ANS
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
read(n);
For(i,,n) read(a[i]);
Rep(i,n,) {
pos=-i;
sum+=a[i]-i; sumcnt++; if(a[i]-i>=pos) now+=a[i]-i,nowcnt++; ans[i]=(now-nowcnt*pos)+((sumcnt-nowcnt)*pos-(sum-now)); cnt[a[i]-i+n]++; now-=pos*cnt[pos+n];
nowcnt-=cnt[pos+n];
} sum=now=sumcnt=nowcnt=;
memset(cnt,,sizeof(cnt));
For(i,,n) {
pos=n-i;
sum+=a[i]-i; sumcnt++;
if(a[i]-i<=pos) now+=a[i]-i,nowcnt++; ans[i+]+=(nowcnt*pos-now)+((sum-now)-(sumcnt-nowcnt)*pos); cnt[a[i]-i+n]++; now-=pos*cnt[pos+n];
nowcnt-=cnt[pos+n];
} LL rs=ans[];
For(i,,n) rs=min(rs,ans[i]);
printf("%lld\n",rs);
Formylove;
}
迷宫
线段树时空复杂度都怎么算怎么ok啊,而且超级好写的啊。。
就是有点卡常,我要加register才能卡过最后两个点。
//Achen
#include<bits/stdc++.h>
#define For(i,a,b) for(register int i=(a);i<=(b);i++)
#define Rep(i,a,b) for(register int i=(a);i>=(b);i--)
#define Formylove return 0
#define inf 1e8
const int N=;
typedef long long LL;
typedef double db;
using namespace std;
int n,m,q,a[][N]; template<typename T>void read(T &x) {
char ch=getchar(); T f=; x=;
while(ch!='-'&&(ch<''||ch>'')) ch=getchar();
if(ch=='-') f=-,ch=getchar();
for(;ch>=''&&ch<='';ch=getchar()) x=x*+ch-''; x*=f;
} void GM(int &x,int y) { if(x>y) x=y; } #define lc x<<1
#define rc ((x<<1)|1)
#define mid ((l+r)>>1)
int sg[N<<][][];
void upd(int x,int l,int r) {
memset(sg[x],/,sizeof(sg[x]));
if(l==r) {
For(i,,n) if(a[i][l]) sg[x][i][i]=;
For(i,,n) Rep(j,i-,) if(a[i][l]&&a[i-][l]) {
GM(sg[x][i][j],sg[x][i-][j]+);
GM(sg[x][j][i],sg[x][i-][j]+);
}
}
else {
For(i,,n) For(j,,n) {
For(k,,n) if(a[k][mid]&&a[k][mid+])
GM(sg[x][i][j],sg[lc][i][k]+sg[rc][k][j]+);
}
}
} void build(int x,int l,int r) {
if(l==r) { upd(x,l,r); return; }
build(lc,l,mid); build(rc,mid+,r);
upd(x,l,r);
} void update(int x,int l,int r,int p1,int p2) {
if(l==r) {
a[p2][p1]^=;
upd(x,l,r); return;
}
if(p1<=mid) update(lc,l,mid,p1,p2);
else update(rc,mid+,r,p1,p2);
upd(x,l,r);
} int tp[][],rs[][],ok;
void merge(int x,int l,int r) {
if(!ok) {
ok=;
For(i,,n) For(j,,n)
tp[i][j]=sg[x][i][j];
}
else {
memset(rs,/,sizeof(rs));
For(i,,n) For(j,,n) {
For(k,,n) if(a[k][l-]&&a[k][l])
GM(rs[i][j],tp[i][k]+sg[x][k][j]+);
}
memcpy(tp,rs,sizeof(rs));
}
} void qry(int x,int l,int r,int ql,int qr) {
if(l>=ql&&r<=qr) { merge(x,l,r); return; }
if(ql<=mid) qry(lc,l,mid,ql,qr);
if(qr>mid) qry(rc,mid+,r,ql,qr);
} #define ANS
int main() {
#ifdef ANS
freopen("maze.in","r",stdin);
freopen("maze.out","w",stdout);
#endif
read(n); read(m); read(q);
For(i,,n) For(j,,m) read(a[i][j]);
build(,,m);
For(cs,,q) {
int o,x,y,z,w;
read(o); read(x); read(y);
if(o==)
update(,,m,y,x);
else {
read(z); read(w);
ok=;
qry(,,m,y,w);
if(tp[x][z]>=inf) puts("-1");
else printf("%d\n",tp[x][z]);
}
}
Formylove;
}
动态数点
从n^2暴力优化到标解蛮容易的,二分长度,st表处理gcd和min值。只是似乎又要卡常了。
看李巨一个排序的复杂度爆踩std。
按a从小到大排序,然后拓展。拓展过的点就不用再拓展了,发现每个点最多被拓展两边,左边一遍右边一遍(3 15 5)。
辉神就更强了,从左到右依次拓展但是每次拓展的中心是上一次拓展的右边界的下一个,这样最坏的情况下也只能卡成nlogv的,而实际远不到上限,跑得飞快。
//Achen
#include<bits/stdc++.h>
#define For(i,a,b) for(int i=(a);i<=(b);i++)
#define Rep(i,a,b) for(int i=(a);i>=(b);i--)
#define Formylove return 0
const int N=;
typedef long long LL;
typedef double db;
using namespace std;
int n,b[N],vis[N],a[N];
int tot,ans; template<typename T>void read(T &x) {
char ch=getchar(); T f=; x=;
while(ch!='-'&&(ch<''||ch>'')) ch=getchar();
if(ch=='-') f=-,ch=getchar();
for(;ch>=''&&ch<='';ch=getchar()) x=x*+ch-''; x*=f;
} struct node {
int pos,a;
friend bool operator <(const node&A,const node&B) {
return A.a<B.a;
}
}p[N]; #define ANS
int main() {
#ifdef ANS
freopen("point.in","r",stdin);
freopen("point.out","w",stdout);
#endif
read(n);
For(i,,n) {
read(a[i]);
p[i].a=a[i];
p[i].pos=i;
}
sort(p+,p+n+);
For(i,,n) {
int l=p[i].pos,r=p[i].pos;
if(vis[l]) continue;
while(l>&&a[l-]>=p[i].a&&a[l-]%p[i].a==)
vis[--l]=;
while(r<n&&a[r+]>=p[i].a&&a[r+]%p[i].a==)
vis[++r]=;
b[l]=r-l;
ans=max(ans,r-l);
}
For(i,,n) tot+=(b[i]==ans);
printf("%d %d\n",tot,ans);
For(i,,n) if(b[i]==ans) printf("%d ",i);
puts("");
Formylove;
}
李巨做法的代码
NOIp2018集训test-10-4/test-10-5 (联考四day1/day2)的更多相关文章
- NOIp2018集训test-10-6/test-10-7 (联考五day1/day2)
昨天考完月考,明天初赛,dcoi2017级今天终于开始停课准备noip了,大概没有比本弱校停课更晚的学校了吧.本来就够菜了,怕是要凉透哦. DAY1 T1石头剪刀布 据说爆搜随便做,但是我觉得我的O( ...
- NOIp2018集训test-9-22(am/pm) (联考三day1/day2)
szzq学长出的题,先orz一下. day1 倾斜的线 做过差不多的题,写在我自己的博客里,我却忘得一干二净,反而李巨记得清清楚楚我写了的. 题目就是要最小化这个东西 $|\frac{y_i-y_j} ...
- NOIp2018集训test-10-21 (联考六day1)
今天被高一狂踩,两个手抖,t1一个1写成2,t3一个+=写成=,所谓失之毫厘谬以千里,直接丢了50分. 完全背包 看到背包体积如此之大物品体积如此之小容易很想到贪心,肯定要先加很多很多的性价比最高的最 ...
- NOIp2018集训test-9-15(联考二day1)
T1.矩阵游戏 水题.每一行最后乘的数为x[i],每一列为y[i],暴力算第一行的列的贡献,每一行的列的贡献是公差为所有列的贡献之和的等差数列,然后每一行再乘上行的贡献求和即为答案. //Achen ...
- NOIp2018集训test-9-7(pm) (联考一day1)
又被辉神吊打了.今天不仅被辉神李巨吊打,还给基本上给全班垫底了. 看到T3就知道是十进制快速幂,全机房考试的当时应该就我会,结果我tm没找到递推. Orz lyc BM直接水过,Orz wys六个fo ...
- 给定整数a1、a2、a3、...、an,判断是否可以从中选出若干个数,使得它们的和等于k(k任意给定,且满足-10^8 <= k <= 10^8)。
给定整数a1.a2.a3.....an,判断是否可以从中选出若干个数,使得它们的和等于k(k任意给定,且满足-10^8 <= k <= 10^8). 分析:此题相对于本节"寻找满 ...
- 2018.10.26 浪在ACM 集训队第四次测试赛
2018.10.26 浪在ACM 集训队第四次测试赛 题目一览表 来源 考察知识点 完成时间 A 生活大爆炸版 石头剪刀布 NOIP 提高组 2014 模拟??? 2018.11.9 B 联合 ...
- gitlab 迁移、升级打怪之路:8.8.5--> 8.10.8 --> 8.17.8 --> 9.5.9 --> 10.1.4 --> 10.2.5
gitlab 迁移.升级打怪之路:8.8.5--> 8.10.8 --> 8.17.8 --> 9.5.9 --> 10.1.4 --> 10.2.5 gitlab 数据 ...
- var a =10 与 a = 10的区别
学习文章------汤姆大叔-变量对象 总结笔记 变量特点: ①变量声明可以存储在变量对象中.②变量不能直接用delete删除. var a =10 与 a = 10的区别: ①a = 10只是为全局 ...
随机推荐
- 【JavaWeb项目】一个众筹网站的开发(六)后台用户权限控制
登陆成功进入控制面板后 左侧的菜单是共同的元素,抽取出来做静态包含 要求必须是按照不同的用户得到不同的菜单 用户做了权限限制,哪个用户能操作哪些内容(链接.按钮.内容) 一.RBAC权限模型 权限管理 ...
- Attribute 实现Aop
1.先定义一个 拦截属性 AopAttribute using System; using System.Collections.Generic; using System.Linq; using S ...
- Android中的Toast重复显示的问题
Toast是Android中用来显示信息的一种机制,和Dialog不一样的是,Toast是没有焦点,而且Toast显示的时间有限,过一定的时间就会自动消失. Toast一般用来提示用户的误操作.但是如 ...
- noip2007 tg day1t1 统计数字
题目描述 某次科研调查时得到了n个自然数,每个数均不超过1500000000(1.5*10^9).已知不相同的数不超过10000个,现在需要统计这些自然数各自出现的次数,并按照自然数从小到大的顺序输出 ...
- badboy设置参数化
概述 1.将录制的检查点设置参数化 2.然后回放看结果 ps.设置检查点教程请看上一篇badboy教程 第一:添加变量 第二:将循环次数.请求参数.检查点设置参数化 第三:设置完毕后,点击回放按钮进行 ...
- Spring 容器初始化方法
Resource resource = new ClassPathResource("/bean.xml"); resource = new FileSystemR ...
- 带头结点的循环单链表----------C语言
/***************************************************** Author:Simon_Kly Version:0.1 Date: 20170520 D ...
- node.js是用来做什么的
Node.js 使用了一个事件驱动.非阻塞式 I/O 的模型,使其轻量又高效.(事件驱动:事件触发过程中,进行决策的一种策略,简单说就是跟随当前时间点上出现的事物,调用可用的资源进行解决该事物,使得不 ...
- Java学习之集合(List接口)
List特有的常见方法:有一个共性特点:都可以操作角标 1.添加 void add(int index, E element); void addAll(int index, collection& ...
- GIT 学习第二天 (二)
工作区和暂存区 工作区: 就是你在电脑里能看到的目录,比如:webgit 文件夹 就是一个工作区 版本库: 工作区有一个隐藏目录 .git ,这个不算工作区,而是Git的版本库 Git的版本库里存了很 ...