数组first,大小为K。构造一个first的排列F。对于无穷序列A:∀∀i,0<=i < K,则A[i]=F[i];K<=i,则 A[i] = A[i-K] – A[i-K+1] + … + (-1)^(K-1) * A[i-1]。给定N,要求排列F最大化A[N]。若有多种排列满足条件,返回字典序最小的排列(逐个比较排列的数值大小)。
1<=K<=50,-1e9<=first[i]<=1e9,0<=N<=1e9
思路
<1> n < k时需要F[n]最大其余升序排列
<2> k为奇数->F[i]+F[i-1]=F[i-k-1]+F[i-1]即F[i]=F[i-k-1];故使F[n%(k+1)]最大
int k=F.size();
res.resize(k);
sort(F.begin(),F.end());
if(k&1||N<k){
N=N%(k+1);
if(N==k){
//最大的F[k];
int p=0;
for(int i=1;i<k;i+=2)res[i]=F[p++];
for(int i=0;i<k;i+=2)res[i]=F[p++];
}else{
//最大的F[N%(k+1)]
for(int i=0;i<k;i++){
if(i<N)res[i]=F[i];
else if(i==N)res[i]=F[k-1];
else res[i]=F[i-1];
}
}return res;
}
<3>k为偶数通过枚举可以得到
Ⅰ[0,k)A[N=i]=F[i];
Ⅱ[k,+∞)
->A[N=k]=F[0]-F[1]+F[2]…..-F[k-1]
->A[N=k+1]=F[1]-F[2]…..+F[k-1]-F[k]=-F[0]+2F[1]-2F[2]…..+2F[k-1];//k+1为奇数
->A[N=k+2]=2F[0]-3F[1]+4F[2]……-4F[k-1];//k+2为奇数
容易发现
Ⅰ当N为奇数时其最后一个是+第一个是-
Ⅱ前N-k项的系数是递增的,后面的系数都是相等的(此时按字典序排)
if(N&1){
int num=k-1;
for(int i=k-1;i>=0;i-=2)res[i]=A[num--];//正值的为升序
for(int i=1;i<min(N-k,k);i+=2)res[i]=A[num--];//前面的负值为降序
for(int i=k-2;i>=N-k;i-=2)res[i]=A[num--];//后面的负值为升序
}else{//同理
int num=k-1;
for(int i=k-2;i>=0;i-=2)res[i]=A[num--];
for(int i=0;i<min(N-k,k);i+=2)res[i]=A[num--];
for(int i=k-1;i>=N-k;i-=2)res[i]=A[num--];
}