CF 675 div2C 数学 让环所有值变为0的最少操作数

http://codeforces.com/contest/675/problem/C

题目大意:

给一个环,标号为1-n,然后能从n回到1.让这个环的值为0,最少需要的操作数是多少?

这道题目呀。。。应该说是自己的问题吧,规律并没有那么难找的,只要我将前缀全部都计算一遍就完全可以找出规律了的。。。然后竟然没有去那么做。

首先我们分析,最多的次数就是n-1.然后我们再看,因为是一个环,那么如果每次前缀和出现了0,就是说明这一段内可以得到0,那么所移动的次数就可以少1.

然后我们在反过来分析,我们要找到这个0的个数,应该怎么找呢?然后我们得出规律,如果某个值重复出现了,就说明他同时存在两边可以同时取值到这个值,并且变为0。然后我们用map<ll, int>m来保存,第一维保存的是前n项的和,第二位保存的是这个和的值出现过几次:例如m[3] = 2的意思就是前缀和是3的次数出现过两次。

例如sum的变化是这样子的2 4 6 4 2.那么就说明4 6 4之间的三个值可以变为0,那么同理2和2之间的值也可以变为0.

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 
 4 typedef long long ll;
 5 map <ll, int> m;
 6 
 7 int main(){
 8     ll n;
 9     scanf("%lld", &n);
10     ll res = n - 1;
11     ll sum = 0;
12     for (int i = 1; i <= n; i++){
13         ll t;
14         cin >> t;
15         sum += t;
16         m[sum]++;
17         res = min(res, n - m[sum]);
18     }
19     printf("%lld
", res);
20     return 0;
21 }
View Code
原文地址:https://www.cnblogs.com/heimao5027/p/5507119.html