hdu6395 /// 分块矩阵快速幂

题目大意:

F(1)=A, F(2)=B,  F(i)=C*F(i-2)+D*F(i-1)+p/i(向下取整)

给定A B C D p n

求F(n)

构造

   矩阵A    *    矩阵B        =          矩阵C

┌ F(n-2) F(n-1) 1  ┐    ┌ 0   C  0  ┐        ┌ F(n-1) F(n)   1   ┐

|      0  0   0    | *   |  1   D  0  |   =    |      0  0   0    |

└  0     0   0 ┘    └ 0  p/i 1 ┘  └  0     0   0 ┘

那么当A为第一项时  A*(B^n)=第n项

因为p/i向下取整所以在 1~n的范围中 p/i的数值是多段相等的

如n=10 p=15 那么1~n中 p/i为 15 7 5 3 3 2 2 1 1 1

改变B中的p/i 分别求B^len 即 B^1 B^1 B^1 B^2 B^2 B^3

已知 p / i = x 那么len = min( p / ( p / i ) , n )  都是int型向下取整

就得到了分块的 B^n

#include <bits/stdc++.h>
using namespace std;
#define INF 0x3f3f3f3f
#define LLINF 0x3f3f3f3f3f3f3f3f3f
#define LL long long
#define mem(i,j) memset(i,j,sizeof(i))
const int N=3;
const int mod=1e9+7;

LL A,B,C,D,p,n;
struct MAT {
    LL a[N][N];
    MAT(){ mem(a,0); }
    MAT operator*(MAT p) {
        MAT res;
        for(int i=0;i<N;i++)
        for(int j=0;j<N;j++)
        for(int k=0;k<N;k++)
            res.a[i][j]=(res.a[i][j]+a[i][k]*p.a[k][j])%mod;
        return res;
    }
}Ans,Pow;
MAT mod_pow(MAT A,int x) {
    MAT res;
    res.a[0][0]=res.a[1][1]=res.a[2][2]=1;
    while(x) {
        if(x&1) res=res*A;
        A=A*A; x>>=1;
    }
    return res;
}
int main()
{
    int t; scanf("%d",&t);
    while(t--) {
        scanf("%lld%lld%lld%lld%lld%lld",&A,&B,&C,&D,&p,&n);
        Ans.a[0][0]=A, Ans.a[0][1]=B, Ans.a[0][2]=1;
        Pow.a[1][0]=Pow.a[2][2]=1;
        Pow.a[0][1]=C, Pow.a[1][1]=D;
        for(int x=3,px;x<=n;x=px+1) {
            px= p/x ? min(p/(p/x),n):n;
            Pow.a[2][1]=p/x;
            MAT t=mod_pow(Pow,px-x+1); // x~px的值都为p/x
            Ans=Ans*t;
        }
        printf("%lld\n",Ans.a[0][1]);
    }

    return 0;
}

原文地址:https://www.cnblogs.com/zquzjx/p/10360768.html

时间: 2024-11-01 20:45:02

hdu6395 /// 分块矩阵快速幂的相关文章

HDU-6395多校7 Sequence(除法分块+矩阵快速幂)

Sequence Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/Others)Total Submission(s): 1731    Accepted Submission(s): 656 Problem Description Let us define a sequence as below F1=A F2=B Fn=C⋅Fn−2+D⋅Fn−1+⌊Pn⌋ Your job is s

HDU6395-Sequence 矩阵快速幂+除法分块

目录 Catalog Solution: (有任何问题欢迎留言或私聊 && 欢迎交流讨论哦 Catalog Problem:Portal传送门 ?原题目描述在最下面. Solution: ?一看矩阵快速幂,再一看怎么多一个变项?\(? \frac{p}{n}?\)? ?我去,\(? \frac{p}{n}?\)这不是前几天写过的一道除法分块经典题吗? ?关于除法分块,请看这里:GYM101652 ?然后,就没有然后了~ AC_Code: #include<bits/stdc++.h&

【做题】SRM701 Div1 Hard - FibonacciStringSum——数学和式&矩阵快速幂

原文链接 https://www.cnblogs.com/cly-none/p/SRM701Div1C.html 题意:定义"Fibonacci string"为没有连续1的01串.现在,给出\(a,b\),定义一个"Fibonacci string"的权值为\(x^a y^b\),其中\(x\)为0的个数,\(y\)为1的个数. 要求对所有长度为\(n\)的"Fibonacci string"的权值求和,对\(10^9 + 7\)取模. \(n

矩阵快速幂刷题系列

来源自http://blog.csdn.net/chenguolinblog/article/details/10309423 hdu 1575 Tr A Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 5587    Accepted Submission(s): 4200 Problem Description A为一个方阵,则Tr

HDU 1757 A Simple Math Problem (矩阵快速幂)

[题目链接]:click here~~ [题目大意]: If x < 10 f(x) = x. If x >= 10 f(x) = a0 * f(x-1) + a1 * f(x-2) + a2 * f(x-3) + -- + a9 * f(x-10); 问f(k)%m的值. [思路]:矩阵快速幂,具体思路看代码吧,注意一些细节. 代码: #include<bits/stdc++.h> using namespace std; typedef long long LL; const

Codeforces Round #291 (Div. 2) E - Darth Vader and Tree (DP+矩阵快速幂)

这题想了好长时间,果断没思路..于是搜了一下题解.一看题解上的"快速幂"这俩字,不对..这仨字..犹如醍醐灌顶啊...因为x的范围是10^9,所以当时想的时候果断把dp递推这一方法抛弃了.我怎么就没想到矩阵快速幂呢.......还是太弱了..sad..100*100*100*log(10^9)的复杂度刚刚好. 于是,想到了矩阵快速幂后,一切就变得简单了.就可以把距离<=x的所有距离的点数都通过DP推出来,然后一个快速幂就解决了. 首先DP递推式很容易想到.递推代码如下: for(

POJ 3233 - Matrix Power Series ( 矩阵快速幂 + 二分)

POJ 3233 - Matrix Power Series ( 矩阵快速幂 + 二分) #include <cstdio> #include <cstring> #include <algorithm> using namespace std; typedef long long LL; #define MAX_SIZE 30 #define CLR( a, b ) memset( a, b, sizeof(a) ) int MOD = 0; int n, k; st

HDU 4990 Reading comprehension(找规律+矩阵快速幂)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4990 Problem Description Read the program below carefully then answer the question. #pragma comment(linker, "/STACK:1024000000,1024000000") #include <cstdio> #include<iostream> #include

hdu 6198(矩阵快速幂)

number number number Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 175    Accepted Submission(s): 119 暴力发现当4 12 33 88 232 和斐波那契数列对比  答案为 第2*k+3个数减1 直接用矩阵快速幂求的F[2*k+3]  然后减1 A=1,B=0; 然后矩阵快速幂2*k