0%

思路讲解

那么注意到入度为2才是这个修改的充要条件,因为这样子修改边的朝向保证了只会增加一个好对数量。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
auto dfs=[&](auto &&dfs,ll u,ll alte)->void{
vis[u]=true;
FOR(i,0,SZ(g[u])-1){
ll v=g[u][i];
if(vis[v]) continue;
bool isop=false;
// 那么注意到入度为2才是这个修改的充要条件
if(SZ(g[u])==2 && isM==false){
alte=1-alte;
if(alte){
ans.pb({v,u});
}else{
ans.pb({u,v});
}
isM=true;
isop=true;
}else{
if(alte){
ans.pb({v,u});
}else{
ans.pb({u,v});
}
}
dfs(dfs,v,1-alte);
if(isop) alte=1-alte;
}
};

AC代码

https://codeforces.com/contest/2112/submission/325852721

心路历程(WA,TLE,MLE……)

思路讲解

简单来说,就是第一次炸了以后还能存活下来的金块,一定能活下来。

那么形式化的理解就是说第一次炸完以后,剩下的空间就足够其他炸弹进行一些精细操作了。

然后枚举+二维前缀和,就可以用二维前缀和来求。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
FOR(i,1,N){
FOR(j,1,M){
Sum[i][j]=Sum[i-1][j]+Sum[i][j-1]+(G[i][j]=='g')-Sum[i-1][j-1];
}
}
ll ans=0;
FOR(i,1,N){
FOR(j,1,M){
if(G[i][j]=='.'){
ll xl=max(i-K+1,1ll),xr=min(i+K-1,N),yl=max(1ll,j-K+1),yr=min(M,j+K-1);
ll lans=Sum[xr][yr]+Sum[xl-1][yl-1]-Sum[xl-1][yr]-Sum[xr][yl-1];
ans=max(ans,Sum[N][M]-lans);
}
}
}

AC代码

https://codeforces.com/contest/2113/submission/325681423

心路历程(WA,TLE,MLE……)

思路讲解

我感觉可以搞dp(结果看了第二个样例觉得不太行)。

那么其实就是局部最优可以推得全局最优,非常经典的贪心。

那么为什么说这个B朝右朝左选一个最大的就最优了?不会相互影响吗?

image

那我们来看一个你认为会相互影响的,可以看到,这个是矛盾的。所以不会相互影响

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
FOR(i,1,N){
++cnt[S[i]-'A'];
if(S[i]=='B'){
L[i]=cnt[0];
}else if(S[i]=='C'){
cnt[0]=0;
}else{

}
}
cnt.assign(10,0);
ROF(i,N,1){
++cnt[S[i]-'A'];
if(S[i]=='B'){
R[i]=cnt[2];
}else if(S[i]=='A'){
cnt[2]=0;
}else{

}
}
FOR(i,1,N){
if(S[i]=='B'){
ans+=max(L[i],R[i]);
}
}

AC代码

https://www.codechef.com/viewsolution/1167971455

心路历程(WA,TLE,MLE……)

写了一个下午,一直WA,思路错了。

思路讲解

主要的收获就是打表

ll Ans[MAXN]={0,2,1,3,5,4};

最重要的就是想出来这个,让3,5靠在一起,这样就直接搞定了,后面的构造是很容易的。

AC代码

https://www.codechef.com/viewsolution/1167807254

心路历程(WA,TLE,MLE……)