- 题目:
给你一个字符串,字符串只有+和-,+代表1,-代表 -1,是正负正负交替进行运算,然后给你q个询问,每个询问给你两个数字L,R,在字符串区间[L, R]中使得这个区间的和为0需要删除的最小个数是多少? - 思路:
求前缀和,如果在这个区间里面删除一个下标为 i 的字符,只会对后面进行影响 前面的和为A = sum[i - 1] - sum[l - 1],后面的和为B = sum[r] - sum[i],修改以后后面的和取相反数,所以就要有 sum[i - 1] - sum[l - 1] = sum[r] - sum[i],也就是sum[i - 1] + sum[i] = sum[r] + sum[l - 1],sum[r],sum[l - 1]已知,然后sum[i - 1]和sum[i]相差1,所以他们相加是奇数,原来未改变的值 x = A + B + (1或者-1),那x一定得是奇数,次数就是1如果是偶数的话,就先删除一个 次数就是2 - 代码:
#include <bits/stdc++.h>
#define fi first
#define se second
#define endl '\n'
#define all(x) x.begin(),x.end()
#define pb push_back
#define PII pair<int,int>
#define ios ios::sync_with_stdio(false); cin.tie(0); cout.tie(0)
#define int long long
using namespace std;
const int N = 3e5 + 100,M = N,mod = 1e9 + 7,INF = 0x3f3f3f3f;
int sum[N];
void solve()
{
int n,m; cin >> n >> m;
string s; cin >> s;
memset(sum,0,sizeof sum);
for(int i = 0;i < n;i ++ )
{
if(i & 1)
{
if(s[i] == '+')
sum[i + 1] = sum[i] - 1;
else
sum[i + 1] = sum[i] + 1;
}
else
{
if(s[i] == '+')
sum[i + 1] = sum[i] + 1;
else
sum[i + 1] = sum[i] - 1;
}
}
while(m -- )
{
int l,r; cin >> l >> r;
int t = sum[r] - sum[l - 1];
if(t == 0) cout << "0" << endl;
else if(t & 1) cout << "1" << endl;
else cout << "2" << endl;
}
}
signed main()
{
ios;int T; cin >> T;
while(T -- ) solve();
return 0;
}
``