0%

思路讲解

要多写,如果实在没有思路就数学化。

参考思路如下。

https://www.luogu.com.cn/article/7xrsn748

不难发现,我们要最小化下面👇。

i=1n(s[i]s[i])2i=1ns[i]2+s[i]22s[i]s[i]\sum_{i=1}^{n}(s[i]-s'[i])^2 \Rightarrow \sum_{i=1}^{n}s[i]^2+s'[i]^2-2s[i]s'[i]

Codeforces Round 1046 (Div. 2)——D. For the Champion

常数分离以后,我们其实就是要最大化👇。

相当于我们要最大化 i=1ns[i]s[i]\sum_{i=1}^{n}s[i]s'[i] 。不过我们发现好像没什么用?非常有用,我们就知道了,1 1 非常重要,要尽量多的出现1 1,其他不重要

当然,如果光有这个想法是不行的。我们还需要用到分块思想。

首先那,分块,我们自然是同时只能按照一个字符串分块的,因此我们按照 ss 可不可以交换分块。

但是,我们按照 ss 分块以后,我们可以再对 ss' 进行分块。这个听起来很抽象是吧?其实也简单,就是说 ss’ 其实如果不是落在整段 ss 可交换块上,可以部分落在 s 的可交换块上,然后我们的策略其实就是尽量多的出现1 1。

AC代码

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

思路讲解

https://leetcode.cn/problems/longest-substring-with-at-least-k-repeating-characters/description/

其实就是双指针。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
void cal(ll uni){
vll cnt(28);
ll l=0,r=0;
ll cur=0,bigk=0;
while (r<SZ(s)) {
if(cur<=uni){
int idx=s[r]-'a';
if(cnt[idx]==0) ++cur;
cnt[idx]++;
if(cnt[idx]==K) ++bigk;
++r;
}else{
int idx=s[l]-'a';
if(cnt[idx]==K) --bigk;
--cnt[idx];
if(cnt[idx]==0) --cur;
++l;
}
if(cur==uni && bigk==cur){
ans=max(ans,r-l);
}
}
}

AC代码

AC

https://leetcode.cn/problems/longest-substring-with-at-least-k-repeating-characters/submissions/658772401/

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

思路讲解

1
2
// 整体思路就是我们如果发现如果两者起始位置不同,那么是不会有相交的,或者相交一次
// 简单而言,就是必须先有一次相交,接着运动方向一样,才能有相交,否则就直接穿过去了
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
// 在同一点并且操作序列相同
if(a==b && opa==opb){
ans+=mn;
}else{
auto f=[&](ll dis){
Point c=oper(a, opa,dis),d=oper(b, opb, dis);
return mandis(c, d);
};
ll l=1,r=mn;
while (l<r) {
ll mid=l+r>>1;
// if(f(mid)<=f(mid+1)){
// 从mid点(或其前)开始,函数开始单调递增
if(f(mid+1)-f(mid)>=0){
r=mid;
}else{
l=mid+1;
}
}
if(f(l)==0){
++ans;
}
}

AC代码

https://atcoder.jp/contests/abc421/submissions/68978595

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

思路讲解

这种题目就是要多想,多写,想办法去除绝对值。

把式子写下来。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
    ll dis=ask('U',mod);
sort(all(A),[&](Point a,Point b){
return 2*2*mod-a.x()-a.y() < 2*2*mod-b.x()-b.y();
});
Point a=A[0];
// 知道了x+y是多少
// mod*2+X+mod*2+Y-a.x()-a.()=dis
ll XY=dis-2*2*mod+a.x()+a.y();
// #ifdef LOCAL
// debug(XY);
// #endif
ask('D',mod);
ask('D', mod);
ask('D',mod);
ll dis2=ask('D', mod);
sort(all(A),[&](Point a,Point b){
return 2*2*mod-a.x()+a.y() < 2*2*mod-b.x()+b.y();
});
a=A[0];
// X+2*mod-x+y-(Y-2*mod)=dis2
// dis2+x-y-2*2*mod
ll X_Y=dis2+a.x()-a.y()-2*2*mod;

AC代码

https://codeforces.com/contest/2136/submission/336079080

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

思路讲解

The Doors 的想法,跑dij。

感觉可以套用这个做法,把距离都变成1,就是要开多少门。

AC代码

https://vjudge.net/solution/63304444

https://vjudge.net/problem/UVA-754

这道题目的UVA版本好像还加了数据,继续测一下。

搞了半天是格式问题,要换两次行。

image

https://vjudge.net/solution/63313110

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