题解 麻烦的杂货店
首先 可以离线下来归并做
然后发现可以对每个询问区间分治
答案一定是左,右边最大值或最左,右边的 构成的区间
于是有一个 的做法
可以 ST 表优化到 ? 没细想
然后正解是这样的:
先转化到前缀和序列上
考虑答案区间,其左右端点一定是相等的,且为区间
于是 ST 表查询区间最左,右的最小值的位置
预处理 分别表示在 前/后离 最远的 满足 且
这样其实构造了一个性质:
设询问区间为 ,则 内的 ,右边同理
并不知道如何想到这样的构造
于是答案即为
复杂度
点击查看代码
#include <bits/stdc++.h>
using namespace std;
#define INF 0x3f3f3f3f
#define N 100010
#define pb push_back
#define ll long long
//#define int long long
int n, m;
char s[N];
int a[N];
namespace force{
int pre[N], ans[N], top;
struct que{int fir, sec, rk;}q[N], sta[N];
vector<int> able[N];
int tl[N<<2], tr[N<<2], val[N<<2];
#define tl(p) tl[p]
#define tr(p) tr[p]
#define val(p) val[p]
#define pushup(p) val(p)=min(val(p<<1), val(p<<1|1))
void build(int p, int l, int r) {
tl(p)=l; tr(p)=r;
if (l==r) {val(p)=pre[l]; return ;}
int mid=(l+r)>>1;
build(p<<1, l, mid);
build(p<<1|1, mid+1, r);
pushup(p);
}
int query(int p, int l, int r) {
if (l<=tl(p)&&r>=tr(p)) return val(p);
int mid=(tl(p)+tr(p))>>1;
if (l<=mid && r>mid) return min(query(p<<1, l, r), query(p<<1|1, l, r));
else if (l<=mid) return query(p<<1, l, r);
else return query(p<<1|1, l, r);
}
void solve() {
for (int i=1; i<=n; ++i) pre[i]=pre[i-1]+a[i];
build(1, 1, n);
for (int i=1; i<=n; ++i)
for (int j=i; j<=n; ++j)
if (pre[j]-pre[i-1]==0 && query(1, i, j)>=pre[i-1]) able[i].pb(j);
for (int i=1; i<=m; ++i) scanf("%d%d", &q[i].fir, &q[i].sec), q[i].rk=i;
sort(q+1, q+m+1, [](que a, que b){return a.sec<b.sec;});
for (int i=1; i<=n; ++i) {
top=0;
for (int j=1; j<=m; ++j) if (q[j].fir<=i&&q[j].sec>=i) sta[++top]=q[j];
int pos=1, now=0;
for (auto it:able[i]) {
while (pos<=top && sta[pos].sec<it) ans[sta[pos].rk]=max(ans[sta[pos].rk], now), ++pos;
now=it-i+1;
}
while (pos<=top) ans[sta[pos].rk]=max(ans[sta[pos].rk], now), ++pos;
}
for (int i=1; i<=m; ++i) printf("%d\n", ans[i]);
}
}
namespace task{
int pre[N], nxt[N], sum[N], buc[N], lg[N];
int stl[20][N], str[20][N], stn[20][N], stp[20][N];
inline int hmin(int a, int b) {return sum[a]<=sum[b]?a:b;}
void init() {
int *l=stl[0], *r=str[0], *u=stn[0], *v=stp[0];
memset(pre, -1, sizeof(pre));
memset(nxt, -1, sizeof(nxt));
memset(buc, -1, sizeof(buc));
for (int i=1; i<=n; ++i) sum[i]=sum[i-1]+a[i];
buc[sum[0]]=0;
for (int i=1; i<=n; ++i) {
if (sum[i-1]>sum[i]) buc[sum[i-1]]=-1;
if (~buc[sum[i]]) pre[nxt[buc[sum[i]]]=i]=buc[sum[i]];
buc[sum[i]]=i;
}
for (int i=1; i<=n; ++i) {
if (~pre[i] && ~pre[pre[i]]) pre[i]=pre[pre[i]];
v[i]=(~pre[i])?i-pre[i]:0;
}
for (int i=n; ~i; --i) {
if (~nxt[i] && ~nxt[nxt[i]]) nxt[i]=nxt[nxt[i]];
u[i]=(~nxt[i])?nxt[i]-i:0;
}
for (int i=1; i<=n; ++i) l[i]=r[i]=i;
#if 0
cout<<"sum: "; for (int i=0; i<=n; ++i) cout<<setw(2)<<sum[i]<<' '; cout<<endl;
cout<<"pos: "; for (int i=0; i<=n; ++i) cout<<setw(2)<<i<<' '; cout<<endl;
cout<<"pre: "; for (int i=0; i<=n; ++i) cout<<setw(2)<<pre[i]<<' '; cout<<endl;
cout<<"nxt: "; for (int i=0; i<=n; ++i) cout<<setw(2)<<nxt[i]<<' '; cout<<endl;
cout<<"u : "; for (int i=0; i<=n; ++i) cout<<setw(2)<<u[i]<<' '; cout<<endl;
cout<<"v : "; for (int i=0; i<=n; ++i) cout<<setw(2)<<v[i]<<' '; cout<<endl;
#endif
}
void build() {
for (int i=1; i<=n; ++i) lg[i]=lg[i-1]+(1<<lg[i-1]==i);
int t=lg[n]-1;
for (int j=1; j<=t; ++j) {
for (int i=0; i+(1<<j)-1<=n; ++i) {
stl[j][i]=hmin(stl[j-1][i], stl[j-1][i+(1<<(j-1))]);
str[j][i]=hmin(str[j-1][i+(1<<(j-1))], str[j-1][i]);
stn[j][i]=max(stn[j-1][i], stn[j-1][i+(1<<(j-1))]);
stp[j][i]=max(stp[j-1][i], stp[j-1][i+(1<<(j-1))]);
}
}
}
inline int qmax(int (*st)[N], int l, int r) {
int t=lg[r-l+1]-1;
return max(st[t][l], st[t][r-(1<<t)+1]);
}
void solve() {
init(); build();
for (int i=1,x,y,l,r,ans; i<=m; ++i) {
scanf("%d%d", &x, &y); --x;
int t=lg[y-x+1]-1;
l=hmin(stl[t][x], stl[t][y-(1<<t)+1]);
r=hmin(str[t][y-(1<<t)+1], str[t][x]);
//cout<<"lr: "<<l<<' '<<r<<endl;
ans=r-l;
if (l>x) ans=max(ans, qmax(stn, x, l-1));
if (r<y) ans=max(ans, qmax(stp, r+1, y));
printf("%d\n", ans);
}
}
}
signed main()
{
freopen("grocery.in", "r", stdin);
freopen("grocery.out", "w", stdout);
scanf("%d%d%s", &n, &m, s+1);
for (int i=1; i<=n; ++i) a[i]=(s[i]=='F')?1:-1;
// force::solve();
task::solve();
return 0;
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现