Codeforces Round #423 Div. 1
A:暴力赋值即可,并查集维护下一个未被赋值的位置。
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define N 2000010
char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
int read()
{
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
return x*f;
}
int T,fa[N],len;
char s[N],ans[N];
int find(int x){return fa[x]==x?x:fa[x]=find(fa[x]);}
signed main()
{
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
T=read();
for (int i=1;i<=2000001;i++) fa[i]=i;
while (T--)
{
scanf("%s",s);int m=strlen(s);
int n=read();
for (int i=1;i<=n;i++)
{
int x=read();
len=max(len,x+m-1);
for (int j=find(x);j<=x+m-1;j=find(j))
ans[j]=s[j-x],fa[j]=find(j+1);
}
}
for (int i=1;i<=len;i++)
if (find(i)==i) ans[i]='a';
printf("%s",ans+1);
return 0;
//NOTICE LONG LONG!!!!!
}
B:显然应该连成菊花套链。
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define N 200010
char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
int read()
{
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
return x*f;
}
int n,k;
bool flag[N];
signed main()
{
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
cin>>n>>k;
if (n%k==2||k==2&&n%k==0) cout<<2*((n-2)/k)+1<<endl;
else if (n%k==1) cout<<2*((n-1)/k)<<endl;
else cout<<2*((n-1)/k+1)<<endl;
for (int i=1;i<=k;i++) flag[i]=1;
for (int i=k+1;i<n;i++)
{
flag[i-k]=0;flag[i]=1;
printf("%d %d\n",i-k,i);
}
for (int i=1;i<=n;i++) if (flag[i]) printf("%d %d\n",n,i);
return 0;
//NOTICE LONG LONG!!!!!
}
C:注意到字符集大小很小询问串长度很短,对每种字符每种长度分别维护bit即可。
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define N 100010
char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
int read()
{
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
return x*f;
}
char s[N],t[N];
int n,q,tree[4][11][N];
int trans(char c)
{
if (c=='A') return 0;
if (c=='T') return 1;
if (c=='G') return 2;
if (c=='C') return 3;
}
int nxt(int x,int m,int r)
{
if (x>r) x-=m;
return x+(r-x)/m*m;
}//<=r u mod m=x mod m
void add(int x,int m,int k,int p)
{
while (k<=n)
{
tree[x][m][k]+=p;
int u=(k-1)/m+1;
u+=u&-u;
k=(u-1)*m+(k-1)%m+1;
}
}
int query(int x,int m,int k)
{
if (k<=0) return 0;
int s=0;
while (k>0)
{
s+=tree[x][m][k];
int u=(k-1)/m+1;
u-=u&-u;
k=(u-1)*m+(k-1)%m+1;
}
return s;
}
signed main()
{
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
scanf("%s",s+1);
n=strlen(s+1);
for (int i=1;i<=n;i++)
for (int j=1;j<=10;j++)
add(trans(s[i]),j,i,1);
q=read();
while (q--)
{
int op=read();
if (op==1)
{
int x=read();
char c=getc();
for (int j=1;j<=10;j++)
add(trans(s[x]),j,x,-1),
add(trans(c),j,x,1);
s[x]=c;
}
else
{
int l=read(),r=read();
scanf("%s",t);int m=strlen(t),ans=0;
for (int i=0;i<m;i++) ans+=query(trans(t[i]),m,nxt(l+i,m,r))-query(trans(t[i]),m,l+i-m);
printf("%d\n",ans);
}
}
return 0;
//NOTICE LONG LONG!!!!!
}
D:先跑一棵MST。对于不在MST中的边,显然要使其满足条件,其权值应比MST中两点路径上的权值最大值小。倍增查一下即可。对于在MST上的边,其权值应比所有覆盖该边的非树边权值小。从小到大进行树链覆盖,并查集维护每个点第一个未被覆盖的祖先即可。
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define N 200010
char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
int read()
{
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
return x*f;
}
int n,m,p[N],dfn[N],f[N],deep[N],fa[N][19],E[N],ans[N],len[N][20],t,cnt;
bool flag[N];
struct data{int to,nxt,i,len;
}edge[N<<1];
struct data2
{
int x,y,z,i;
bool operator <(const data2&a) const
{
return z<a.z;
}
}e[N];
void addedge(int x,int y,int i,int z){t++;edge[t].to=y,edge[t].nxt=p[x],edge[t].i=i,edge[t].len=z,p[x]=t;}
int find(int x){return f[x]==x?x:f[x]=find(f[x]);}
void dfs(int k)
{
for (int i=p[k];i;i=edge[i].nxt)
if (edge[i].to!=fa[k][0])
{
fa[edge[i].to][0]=k;
E[edge[i].to]=edge[i].i;
len[edge[i].to][0]=edge[i].len;
deep[edge[i].to]=deep[k]+1;
dfs(edge[i].to);
}
}
int lca(int x,int y)
{
if (deep[x]<deep[y]) swap(x,y);
for (int j=18;~j;j--) if (deep[fa[x][j]]>=deep[y]) x=fa[x][j];
if (x==y) return x;
for (int j=18;~j;j--) if (fa[x][j]!=fa[y][j]) x=fa[x][j],y=fa[y][j];
return fa[x][0];
}
void cover(int x,int u,int y)
{
x=find(x);
while (deep[x]>deep[u])
{
ans[E[x]]=y-1;
f[x]=find(fa[x][0]);
x=find(x);
}
}
signed main()
{
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
n=read(),m=read();
for (int i=1;i<=m;i++) e[i].x=read(),e[i].y=read(),e[i].z=read(),e[i].i=i;
sort(e+1,e+m+1);
for (int i=1;i<=n;i++) f[i]=i;
for (int i=1;i<=m;i++)
if (find(e[i].x)!=find(e[i].y))
{
f[find(e[i].x)]=find(e[i].y);
addedge(e[i].x,e[i].y,e[i].i,e[i].z),addedge(e[i].y,e[i].x,e[i].i,e[i].z);
flag[i]=1;
}
fa[1][0]=1;dfs(1);
for (int j=1;j<=18;j++)
for (int i=1;i<=n;i++)
fa[i][j]=fa[fa[i][j-1]][j-1],
len[i][j]=max(len[i][j-1],len[fa[i][j-1]][j-1]);
for (int i=1;i<=n;i++) f[i]=i;
for (int i=1;i<=m;i++)
if (!flag[i])
{
int x=e[i].x,y=e[i].y,u=lca(x,y);
cover(x,u,e[i].z);cover(y,u,e[i].z);
for (int j=18;~j;j--)
{
if (deep[fa[x][j]]>=deep[u]) ans[e[i].i]=max(ans[e[i].i],len[x][j]),x=fa[x][j];
if (deep[fa[y][j]]>=deep[u]) ans[e[i].i]=max(ans[e[i].i],len[y][j]),y=fa[y][j];
}
ans[e[i].i]--;
}
for (int i=2;i<=n;i++) if (find(i)==i) ans[E[i]]=-1;
for (int i=1;i<=m;i++) printf("%d ",ans[i]);
return 0;
//NOTICE LONG LONG!!!!!
}
E:考虑如何判断某循环节长度是否合法,显然只要不存在字符不同(不包括?)的距离为其倍数的两位置即可。考虑求每种距离各有多少对字符不同。https://www.cnblogs.com/Gloid/p/9452441.html。然后暴力枚举倍数判断即可。略卡常,似乎FFT比NTT快。
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define N 1100000
#define P 998244353
char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
int read()
{
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
return x*f;
}
int T,n,a[N],b[N],c[N],f[N],r[N],ans[N];
char s[N];
void inc(int &x,int y){x+=y;if (x>=P) x-=P;}
int ksm(int a,int k)
{
int s=1;
for (;k;k>>=1,a=1ll*a*a%P) if (k&1) s=1ll*s*a%P;
return s;
}
int inv(int a){return ksm(a,P-2);}
void DFT(int *a,int n,int g)
{
for (int i=0;i<n;i++) r[i]=(r[i>>1]>>1)|(i&1)*(n>>1);
for (int i=0;i<n;i++) if (i<r[i]) swap(a[i],a[r[i]]);
for (int i=2;i<=n;i<<=1)
{
int wn=ksm(g,(P-1)/i);
for (int j=0;j<n;j+=i)
{
int w=1;
for (int k=j;k<j+(i>>1);k++,w=1ll*w*wn%P)
{
int x=a[k],y=1ll*w*a[k+(i>>1)]%P;
a[k]=(x+y)%P,a[k+(i>>1)]=(x-y+P)%P;
}
}
}
}
void mul(int *a,int *b,int n)
{
DFT(a,n,3),DFT(b,n,3);
for (int i=0;i<n;i++) a[i]=1ll*a[i]*b[i]%P;
DFT(a,n,inv(3));
int t=inv(n);
for (int i=0;i<n;i++) a[i]=1ll*a[i]*t%P;
}
signed main()
{
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
T=read();
while (T--)
{
n=read();scanf("%s",s+1);
int t=1;while (t<(n<<1)) t<<=1;
for (int i=0;i<t;i++) a[i]=b[i]=c[i]=0;
for (int i=0;i<t;i++) f[i]=0;
for (int i=1;i<=n;i++) if (s[i]=='V') a[i]=1;
for (int i=0;i<n;i++) f[i]=2*(s[n-i]=='K');
mul(a,f,t);
for (int i=0;i<t;i++) f[i]=0;
for (int i=1;i<=n;i++) if (s[i]=='K') b[i]=8;
for (int i=0;i<n;i++) f[i]=s[n-i]=='V';
mul(b,f,t);
for (int i=0;i<t;i++) f[i]=0;
for (int i=1;i<=n;i++) if (s[i]=='V') c[i]=1;
for (int i=0;i<n;i++) f[i]=(P-4*(s[n-i]=='K'))%P;
mul(c,f,t);
int u=0;
for (int i=1;i<=n;i++)
{
bool flag=0;
for (int j=i;j<=n;j+=i)
if (a[n-j]+b[n-j]+c[n-j]) {flag=1;break;}
if (!flag) ans[++u]=i;
}
printf("%d\n",u);
for (int i=1;i<=u;i++) printf("%d ",ans[i]);printf("\n");
}
return 0;
//NOTICE LONG LONG!!!!!
}
F:容易想到拆点bfs,点数过多。注意到只要边还没消失就可以在上面反复横跳,每隔2s就能返回一次原来的点。于是只将每个点根据时刻奇偶性拆成两个点。拆完后重建一下图,根据所连点的奇偶性稍微调整一下边的起止时间。
这样可以在一个点逗留的时间段是连续(以2s为单位)的。考虑求出每个点最早什么时候能到,最晚什么时候走,这样就能得到答案了。
用边更新答案。考虑将所有已确定最早能何时经过的边扔进小根堆。每次取出堆顶对该边终点进行更新。然后根据该终点信息更新以其为起点的所有尚未确定最早经过时间的边。若该点最晚离开时间超过了边的出现时间,就确定其最早经过时间。容易发现这样得到的时间一定是最优的,因为要么是其出现时间,要么是当前最早经过的边的时间。否则不管。为保证复杂度需要提前将以某点为起点的边按出现时间从小到大排序。大约就是跑了个魔改dij。
另一种等价实现方法是一开始就把所有边扔进堆,具体见代码。
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<queue>
#include<vector>
#include<cassert>
using namespace std;
#define ll long long
#define N 500010
#define inf 1010000000
#define odd(i) ((i)+n)
#define even(i) (i)
char getc(){char c=getchar();while ((c<'A'||c>'Z')&&(c<'a'||c>'z')&&(c<'0'||c>'9')) c=getchar();return c;}
int gcd(int n,int m){return m==0?n:gcd(m,n%m);}
int read()
{
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=(x<<1)+(x<<3)+(c^48),c=getchar();
return x*f;
}
int n,m,t,first[N<<1],last[N<<1],cur[N<<1];
struct data
{
int x,y,l,r;
bool operator <(const data&a) const
{
return l>a.l;
}
};
priority_queue<data> q;
vector<data> e[N<<1];
void addedge(int x,int y,int l,int r){if (l>r) return;t++;q.push((data){x,y,l,r});}
signed main()
{
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
freopen("a.out","w",stdout);
#endif
n=read(),m=read();
for (int i=1;i<=m;i++)
{
int x=read(),y=read(),l=read(),r=read();
addedge(odd(x),even(y),l+(l%2==0),r-(r&1));
addedge(even(x),odd(y),l+(l&1),r-(r%2==0));
addedge(odd(y),even(x),l+(l%2==0),r-(r&1));
addedge(even(y),odd(x),l+(l&1),r-(r%2==0));
}
for (int i=1;i<=n*2;i++) first[i]=inf,last[i]=-1;
first[1]=last[1]=0;
while (!q.empty())
{
data u=q.top();q.pop();
if (last[u.x]>=u.l)
{
if (first[u.x]>=u.r) continue;
u.l=max(first[u.x],u.l);
last[u.y]=max(last[u.y],u.r);
first[u.y]=min(first[u.y],u.l+1);
while (cur[u.y]<e[u.y].size()&&last[u.y]>=e[u.y][cur[u.y]].l)
{
data v=e[u.y][cur[u.y]++];
if (first[u.y]>=v.r) continue;
v.l=max(first[v.x],v.l);
last[v.y]=max(last[v.y],v.r);
first[v.y]=min(first[v.y],v.l+1);
q.push(v);
}
}
else e[u.x].push_back(u);
}
//for (int i=1;i<=n*2;i++) cout<<first[i]<<' '<<last[i]<<endl;
if (min(first[odd(n)],first[even(n)])>=inf) cout<<-1;
else cout<<min(first[odd(n)],first[even(n)]);
return 0;
//NOTICE LONG LONG!!!!!
}
Codeforces Round #423 Div. 1的更多相关文章
- Codeforces Round #423 (Div. 1, rated, based on VK Cup Finals)
Codeforces Round #423 (Div. 1, rated, based on VK Cup Finals) A.String Reconstruction B. High Load C ...
- Codeforces Round #423 (Div. 2)
codeforces 423 A. Restaurant Tables [水题] //注意,一个人选座位的顺序,先去单人桌,没有则去空的双人桌,再没有则去有一个人坐着的双人桌.读清题意. #inclu ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) E. DNA Evolution 树状数组
E. DNA Evolution 题目连接: http://codeforces.com/contest/828/problem/E Description Everyone knows that D ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) D. High Load 构造
D. High Load 题目连接: http://codeforces.com/contest/828/problem/D Description Arkady needs your help ag ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) C. String Reconstruction 并查集
C. String Reconstruction 题目连接: http://codeforces.com/contest/828/problem/C Description Ivan had stri ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) A,B,C
A.题目链接:http://codeforces.com/contest/828/problem/A 解题思路: 直接暴力模拟 #include<bits/stdc++.h> using ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) Problem E (Codeforces 828E) - 分块
Everyone knows that DNA strands consist of nucleotides. There are four types of nucleotides: "A ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) Problem D (Codeforces 828D) - 贪心
Arkady needs your help again! This time he decided to build his own high-speed Internet exchange poi ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) Problem C (Codeforces 828C) - 链表 - 并查集
Ivan had string s consisting of small English letters. However, his friend Julia decided to make fun ...
- Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) Problem A - B
Pronlem A In a small restaurant there are a tables for one person and b tables for two persons. It i ...
随机推荐
- Hibernate各种基本注解及一对一(多)关系映射采坑笔记
hibernate提供两种方式配置关系映射,一种XMl配置,一种注解.SpringBoot已经自带了hibernate注解方式,我也是特别喜欢使用注解,特此记下常用的知识点. 1.基本注解 @Tabl ...
- Spring Boot 2.0(八):Spring Boot 集成 Memcached
Memcached 介绍 Memcached 是一个高性能的分布式内存对象缓存系统,用于动态Web应用以减轻数据库负载.它通过在内存中缓存数据和对象来减少读取数据库的次数,从而提高动态.数据库驱动网站 ...
- H5 id选择器
09-id选择器 迟到毁一生 早退穷三代 按时上下班 必成高富帅 <!DOCTYPE html> <html lang="en"> <head> ...
- [2019BUAA软工助教]第一次阅读 - 小结
[2019BUAA软工助教]第一次阅读 - 小结 一.评分规则 总分 16 分,附加 2 分,共 18 分 markdown格式统一且正确 - 2分 不统一:扣 1 分 不正确:扣 1 分(例如使用代 ...
- iOS保持App真后台运行
https://www.jianshu.com/p/d466f2da0d33 在我看来,苹果系统与安卓系统最直观的区别就是后台处理方式了吧,安卓手机一旦开启了很多app放到后台,即使前台什么也不做,就 ...
- Form的is_valid校验规则及验证顺序
一.验证顺序 查看form下的源码了解顺序 BaseForm为基类,中间包含了is_valid校验方法 @html_safe class BaseForm: ......... self.is_b ...
- Notepad++远程连接Linux系统
首先在官网下载 https://notepad-plus-plus.org/news/notepad-7.6.4-released.html 在命令行数输入ifconfig 查看自己的Linux的ip ...
- Linux查看硬件等基本参数
http://www.cnblogs.com/xd502djj/archive/2011/02/28/1967350.html
- Velocity中为什么要使用{}来明确标识变量
原因 比如在页面中,页面中有一个$someonename,此时,Velocity将把someonename作为变量名,若我们程序是想在someone这 个变量的后面紧接着显示name字符,则上面的标签 ...
- [转帖]SQL Server 索引中include的魅力(具有包含性列的索引)
SQL Server 索引中include的魅力(具有包含性列的索引) http://www.cnblogs.com/gaizai/archive/2010/01/11/1644358.html 上个 ...