大意是有一排石子,每一堆有a[i]个,目标状态每一堆有b[i]个,每一步可以从一堆中取出一个石子转移到相邻的一个,其中1和n也算相邻也即环形。问最少步数。
比赛的时候写了个按照步数贪心的做法,FST了,当时想的贪心是从1到n/2枚举步数,for每一个需要石子的堆i,从(i+d)%n与(i-d)%n中看是否可以转移。
比赛结束自己想到一个反例
1 0 1 0 0
0 1 0 1 0
答案应当是2,但是我那个贪心结果会成3。
后来看了下别人做法,大致有2种,一种是最优解中会存在某些点,这些点不会有穿越他们的MOVE,所以可以枚举每个点作为开始,将环形转为线性。
答案是每个a与b的前缀和之差的和。
还有一种做法是做一个c[i]=a[i]-b[i]的数组,sort之后,取中位数作为target。答案是所有值与中位数之差的和。
下面贴第一种解法的代码
1 class MoveStones 2 { 3 public: 4 long long get(vector a, vector b) { 5 long long s1=0,s2=0; 6 int n=a.size(); 7 for (int i=0;i