给你n个数,分别是a[1],a[2],...,a[n]。求一个最长的区间[x,y],使得区间中的数(a[x],a[x+1],a[x+2],...,a[y-1],a[y])的和能被7整除。
输出区间长度。若没有符合要求的区间,输出0。
The first line of input contains NN (1 \leq N \leq 50,0001≤N≤50,000). The next NN
lines each contain the NN integer IDs of the cows (all are in the range
0 \ldots 1,000,0000…1,000,000).
Please output the number of cows in the largest consecutive group whose IDs sum
to a multiple of 7. If no such group exists, output 0.
这个题肯定不能直接模拟,你要是暴力枚举端点,看看数据范围。。。。50000^3 下辈子都过不去
我们只要先预处理前缀和,然后用pre[r]-pre[l]就是区间和了,这样只要再那他%7就可以判断了,最后求最大长度就可以了!
我们可以先直接求%7意义下的前缀和,然后只要看看余数的重复就可以了。
这样的话瞬间就简单了 我们只要求出相同的一个余数第一次和最后一次之间的长度即是最长长度! 但是我们不知道哪个余数最长,所以: 枚举0~6 共7个余数各自的最长长度,再在他们7个里找最长的!
#include <bits/stdc++.h>
using namespace std;
#define IOS ios::sync_with_stdio(false); cin.tie(0); cout.tie(0)
typedef long long ll;
const int N = 5e4 + 10;
int n, a[N], first[N], last[N];
int main() {
cin >> n;
for (int i = 1; i <= n; ++i) {
cin >> a[i];
a[i] = (a[i] + a[i - 1]) % 7;
}
for (int i = n; i >= 1; i--) first[a[i]] = i;
for (int i = 1; i <= n; ++i) last[a[i]] = i;
int res = 0;
for (int i = 0; i < 6; ++i) res = max(res, last[i] - first[i]);
cout << res;
return 0;
}
洛谷 P3131 [USACO16JAN]Subsequences Summing to Sevens S
原文:https://www.cnblogs.com/all-taker/p/12976783.html