2019陕西省赛题解
A 数位dp
B 欧拉路径判定
#include<bits/stdc++.h> using namespace std; typedef long long ll; typedef pair<int,int> pll; const int N=500005; const int inf=0x3f3f3f3f; int p[N]; int n,m; vector<char> g[N]; int in[N],out[N]; int num; int find(int x){ if(p[x]!=x){ p[x]=find(p[x]); } return p[x]; } int main(){ int t; ios::sync_with_stdio(false); cin>>t; while(t--){ cin>>n>>m; int i,j; num=0; for(i=0;i<n*m;i++){ p[i]=i; g[i].clear(); in[i]=out[i]=0; } for(i=0;i<n;i++){ for(j=0;j<m;j++){ char c; cin>>c; g[i].push_back(c); } } for(i=0;i<n;i++){ for(j=0;j<m;j++){ int x; cin>>x; int dx,dy; if(g[i][j]=='u'){ dx=i-x; dy=j; } else if(g[i][j]=='d'){ dx=i+x; dy=j; } else if(g[i][j]=='r'){ dx=i; dy=j+x; } else{ dx=i; dy=j-x; } if(dx<0||dx>=n||dy<0||dy>=m) continue; int tmp1=dx*m+dy; int tmp2=i*m+j; int pa=find(tmp1); int pb=find(tmp2); in[tmp1]++,out[tmp2]++; if(pa!=pb){ p[pa]=pb; num++; } } } int sig1=0; int sig2=0; for(i=0;i<n*m;i++) if(in[i]>out[i]) sig1+= in[i]-out[i]; else sig2 += out[i]-in[i]; if(num==n*m-1&&sig1<=1&&sig2<=1)cout<<"Yes"<<endl; else cout<<"No"<<endl; } return 0; }
C 思维字符串去重
#include<cstdio> #include<cstring> #define LL long long const int maxn=1e6+5; char s[maxn]; LL a[5]={0}; int main() { int T; scanf("%d",&T); while(T--) { memset(a,0,sizeof a); scanf("%s",s); LL l=(LL)strlen(s); for(int i=0;s[i]!='\0';i++) { if(s[i]=='0') a[0]++; if(s[i]=='6') a[1]++; if(s[i]=='8') a[2]++; if(s[i]=='9') a[3]++; } LL ans=(l+1)*l/2; LL x=a[0]*(a[0]+1)/2; LL y=a[2]*(a[2]+1)/2; LL z=a[1]*a[3]; ans=ans-x-y-z; if(!(a[1]==l||a[3]==l)) ans++; printf("%lld\n",ans); } return 0; }
E 二分check
#include<bits/stdc++.h> using namespace std; typedef long long ll; const int N=3e5+10; int n,k; string s; bool check(int x){ int i; int cnt=0; for(i=n;i>=1;){ if(s[i]=='1'){ cnt++; i=i-x; } else{ i--; } } return cnt<=k; } int main(){ ios::sync_with_stdio(false); int t; cin>>t; while(t--){ cin>>n>>k; cin>>s; s=" "+s; int l=1,r=n; int num=0; for(int i=1;i<=n;i++){ if(s[i]=='0') num++; } if(num==n){ cout<<0<<endl; continue; } while(l<r){ int mid=l+r>>1; if(check(mid)) r=mid; else l=mid+1; } cout<<l<<endl; } }
F 思维签到
#include<bits/stdc++.h> using namespace std; typedef long long ll; const int N=5005; const int inf=0x3f3f3f3f; const ll y=2e9; int main(){ ll a,b,c; int t; scanf("%d",&t); while(t--){ scanf("%lld%lld%lld",&a,&b,&c); if(c>a+b){ printf("-1\n"); continue; } if(c==a+b){ printf("%lld\n",a+b+1); continue; } ll x=a+b-c; int f=0; for(ll i=1;i<=sqrt(x);i++){ if((x/i)<=a||(x/i)<=c)break; if(x%i==0){ f=1; printf("%lld\n",x/i); break; } } if(!f)printf("-1\n"); } return 0; }
I dfs+线段树
#include<bits/stdc++.h> using namespace std; typedef long long ll; typedef pair<int,int> pll; const int N=200005; const int inf=0x3f3f3f3f; int h[N],ne[N],e[N],idx; char w[N]; int dfn[N],times; struct node{ int l,r; int sum; int lazy; }tr[N<<2]; int sz[N],n; void add(int a,int b,char c){ e[idx]=b,ne[idx]=h[a],w[idx]=c,h[a]=idx++; } bool solve(int u){ int i; int cnt[27]={0}; for(i=h[u];i!=-1;i=ne[i]){ int j=e[i]; cnt[w[i]-'a']++; } int flag=0; for(i=0;i<26;i++){ if(cnt[i]>2){ return false; } if(cnt[i]==2){ if(flag) return false; flag++; } } return true; } bool check(){ int i; for(i=1;i<=n;i++){ if(!solve(i)) return false; } return true; } void dfs(int u,int fa){ dfn[u]=++times; int i; sz[u]=1; for(i=h[u];i!=-1;i=ne[i]){ int j=e[i]; if(j==fa) continue; dfs(j,u); sz[u]+=sz[j]; } } void build(int u,int l,int r){ if(l==r){ tr[u]={l,r,0,0}; } else{ tr[u]={l,r,0,0}; int mid=l+r>>1; build(u<<1,l,mid); build(u<<1|1,mid+1,r); } } void pushup(int u){ tr[u].sum=tr[u<<1].sum+tr[u<<1|1].sum; } void pushdown(int u){ int x=tr[u].lazy; tr[u<<1].sum=(tr[u<<1].r-tr[u<<1].l+1); tr[u<<1|1].sum=(tr[u<<1|1].r-tr[u<<1|1].l+1); tr[u<<1].lazy=tr[u<<1|1].lazy=x; tr[u].lazy=0; } void modify(int u,int l,int r,int k){ if(tr[u].l>=l&&tr[u].r<=r){ tr[u].sum=k*(tr[u].r-tr[u].l+1); tr[u].lazy=k; return ; } if(tr[u].lazy) pushdown(u); int mid=tr[u].l+tr[u].r>>1; if(l<=mid) modify(u<<1,l,r,k); if(r>mid) modify(u<<1|1,l,r,k); pushup(u); } int main(){ ios::sync_with_stdio(false); int t; cin>>t; while(t--){ cin>>n; int i; idx=0,times=0; for(i=0;i<=n+5;i++){ h[i]=-1; } for(i=1;i<n;i++){ int a,b; char c; cin>>a>>b>>c; add(a,b,c); add(b,a,c); } if(!check()){ cout<<0<<endl; continue; } dfs(1,-1); build(1,1,n); for(i=1;i<=n;i++){ map<char,int> m1; for(int j=h[i];j!=-1;j=ne[j]){ int k=e[j]; if(!m1[w[j]]){ m1[w[j]]=k; continue; } int f1=m1[w[j]]; int f2=k; if(dfn[f1]>dfn[i]&&dfn[f2]>dfn[i]){ if(dfn[f1]>dfn[f2]) swap(f1,f2); modify(1,1,dfn[f1]-1,1); if(dfn[f1]+sz[f1]<=n){ modify(1,dfn[f1]+sz[f1],dfn[f2]-1,1); } if(dfn[f2]+sz[f2]<=n) modify(1,dfn[f2]+sz[f2],n,1); } else if(dfn[f1]>dfn[i]&&dfn[f2]<dfn[i]){ modify(1,dfn[i],dfn[f1]-1,1); if(dfn[f1]+sz[f1]<=n) modify(1,dfn[f1]+sz[f1],dfn[i]+sz[i]-1,1); } else if(dfn[f1]<dfn[i]&&dfn[f2]>dfn[i]){ modify(1,dfn[i],dfn[f2]-1,1); if(dfn[f2]+sz[f2]<=n) modify(1,dfn[f2]+sz[f2],dfn[i]+sz[i]-1,1); } break; } } cout<<n-tr[1].sum<<endl; } return 0; }
K 最短路,额外维护d
#include<bits/stdc++.h> using namespace std; typedef long long ll; typedef pair<ll,int> pll; const int N=2e6+10; const int inf=0x3f3f3f3f; int h[N],ne[N],e[N],idx; int n,m,k; int pos[N]; ll dis[N],st[N]; int d[N],w[N]; void add(int a,int b,int c){ e[idx]=b,ne[idx]=h[a],w[idx]=c,h[a]=idx++; } void dij(){ int i; for(i=1;i<=n;i++){ dis[i]=1e18; st[i]=0; } priority_queue<pll,vector<pll>,greater<pll> > q; for(i=1;i<=k;i++){ q.push({0,pos[i]}); dis[pos[i]]=0; d[pos[i]]=0; } while(q.size()){ auto t=q.top(); q.pop(); if(d[t.second]){ d[t.second]=max(d[t.second]-1,0); continue; } if(st[t.second]){ continue; } st[t.second]=1; dis[t.second]=t.first; for(i=h[t.second];i!=-1;i=ne[i]){ int j=e[i]; if(st[j]) continue; q.push({t.first+w[i],j}); } } if(dis[1]==1e18) cout<<-1<<endl; else cout<<dis[1]<<endl; return ; } int main(){ ios::sync_with_stdio(false); int t; cin>>t; while(t--){ int i; idx=0; cin>>n>>m>>k; for(i=1;i<=n;i++) h[i]=-1; for(i=1;i<=k;i++){ cin>>pos[i]; } for(i=1;i<=n;i++){ cin>>d[i]; } for(i=1;i<=m;i++){ int a,b,c; cin>>a>>b>>c; add(a,b,c); add(b,a,c); } dij(); } return 0; }
L 签到
没有人不辛苦,只有人不喊疼