题目链接:https://nanti.jisuanke.com/t/38222
题意:定义F(X)为一个斐波那契函数(F(1) = F(2) = 1),给定一个整型大数w,若满足w = F(F(s1))+F(F(s2))+....F(F(sk))且任意sisj(1<=i,j<=k,且ij),则输出所有解中字典序最小的序列S,若不满足则输出-1
思路:看w的范围可以判断这是个大数,先给F(F(n))打个表,在longlong范围内只能打出几个数,然后发现增长非常快,w范围内应该没有几个数,而且只有n<=5会出现取值情况有优先解的情况,n>5之后只有有解和无解的区别,所以想到先把所有小于w的F(F(n))都打表,然后从大到小判断w可不可以减去该值,n<=5之后特判(我直接枚举),然后这时候发现java暴力打表空间打不下,于是想到矩阵快速幂,c++矩阵快速幂t了......最后看到群里的大佬说用py,贼快,于是...发现py真是个神奇的语言(然后发现省赛不能用神奇的python,于是老老实实又写了java....代码附在后面)
代码:(python3.7)
def mut(x,y):
c = [[0,0],[0,0]]
c[0][0] = x[0][0]*y[0][0]+x[0][1]*y[1][0]
c[0][1] = x[0][0]*y[0][1]+x[0][1]*y[1][1]
c[1][0] = x[1][0]*y[0][0]+x[1][1]*y[1][0]
c[1][1] = x[1][0] * y[0][1] + x[1][1] * y[1][1]
return c
def power(y):
p = [[1,1],[1,0]]
q = [[1,0],[0,1]]
while(y!=1):
if (y%2==1):
y -=1
q = mut(p,q)
else:
y/=2
p =mut(p,p)
return mut(p,q)
p = [[1,1],[1,0]]
a = [0,1,1,1]
for i in range(4,30):
y = power(i-2)
x = y[0][0]+y[1][0]
y = power(x-2)
x = y[0][0]+y[1][0]
a.append(x)
t = int(input())
for i in range(t):
w = int(input())
ans = []
for j in range(29,5,-1):
if w>=a[j]:
w-=a[j]
ans.append(j)
v = len(ans)
if w>10:
print("-1")
continue
if w==1:
ans.append(1)
if w==2:
ans = ans+[2,1]
if w==3:
ans = ans+[3,2,1]
if w==4:
ans = ans+[4,2,1]
if w==5:
ans = ans+[4,3,2,1]
if w==6:
ans = ans+[5,1]
if w==7:
ans = ans+[5,2,1]
if w==8:
ans = ans+[5,3,2,1]
if w==9:
ans = ans+[5,4,2,1]
if w==10:
ans = ans+[5,4,3,2,1]
v = len(ans)
for i in range(v-1,0,-1):
print(ans[i],end=' ')
print(ans[0])
虽然python非常nice,但是一周后发现省赛并没有python编译环境....写了个java,一百多行的java....真是魔鬼
import java.lang.reflect.Array;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.util.*;
import java.text.*;
public class Main {
static Matrix mul(Matrix a, Matrix b) {
Matrix c = new Matrix();
for(int i = 0;i<2;i++) {
for(int j = 0;j<2;j++) {
c.m[i][j] = BigInteger.ZERO;
for(int k = 0;k<2;k++)
c.m[i][j] = (c.m[i][j].add(a.m[i][k].multiply(b.m[k][j])));
}
}
return c;
}
static Matrix cal(Matrix a, BigInteger exp) {
Matrix p = new Matrix(), q = new Matrix();
p = a;
for(int i = 0;i<2;i++) {
for(int j = 0;j<2;j++) {
q.m[i][j] = BigInteger.ZERO;
}
q.m[i][i] = BigInteger.ONE;
}
while(exp.compareTo(BigInteger.ONE)!=0) {
if(exp.mod(BigInteger.valueOf(2)).compareTo(BigInteger.ONE)==0) {
exp = exp.subtract(BigInteger.ONE);
q = mul(p,q);
}
else {
exp = exp.divide(BigInteger.valueOf(2));
p = mul(p,p);
}
}
return mul(p,q);
}
public static void main(String[] args) {
int f[] = new int[100];
f[1] = f[2] = 1;
Scanner cin = new Scanner(System.in);
int ans[] = new int[40];
int cnt = 0;
BigInteger res[] = new BigInteger[40];
for(int i = 5;i<30;i++) {
Matrix x = new Matrix();
x.m[0][0] = x.m[0][1] = x.m[1][0] = BigInteger.ONE;
x.m[1][1] = BigInteger.ZERO;
Matrix a = new Matrix();
a = cal(x,BigInteger.valueOf(i-2));
BigInteger y;
y = a.m[0][0].add(a.m[1][0]);
a = cal(x,y.subtract(BigInteger.valueOf(2)));
y = a.m[0][0].add(a.m[1][0]);
res[i] = y;
}
int t = cin.nextInt();
while(t>0) {
t--;
BigInteger w;
cnt = 0;
w = cin.nextBigInteger();
for(int i = 29;i>=6;i--) {
BigInteger y;
y = res[i];
if(w.compareTo(y)>=0) {
w = w.subtract(y);
ans[cnt] = i;
cnt++;
}
}
if(w.compareTo(BigInteger.valueOf(10))==0) {
ans[cnt++] = 5;
ans[cnt++] = 4;
ans[cnt++] = 3;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(9))==0) {
ans[cnt++] = 5;
ans[cnt++] = 4;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(8))==0) {
ans[cnt++] = 5;
ans[cnt++] = 3;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(7))==0) {
ans[cnt++] = 5;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(6))==0) {
ans[cnt++] = 5;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(5))==0) {
ans[cnt++] = 4;
ans[cnt++] = 3;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(4))==0) {
ans[cnt++] = 4;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(3))==0) {
ans[cnt++] = 3;
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(2))==0) {
ans[cnt++] = 2;
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
else if(w.compareTo(BigInteger.valueOf(1))==0) {
ans[cnt++] = 1;
w = BigInteger.valueOf(0);
}
if(w.compareTo(BigInteger.valueOf(0))==0) {
for(int i = cnt-1;i>0;i--) {
System.out.print(ans[i]+" ");
}
System.out.println(ans[0]);
}
else {
System.out.println("-1");
}
}
}
}
class Matrix{
BigInteger m[][] = new BigInteger[5][5];
}