poj3233 题解 矩阵乘法 矩阵快速幂
题意:求S = A + A2 + A3 + … + Ak.(mod m)
这道题很明显可以用矩阵乘法,但是这道题的矩阵是分块矩阵,
分块矩阵概念如下:当一个矩阵A中的单位元素aij不是一个数值而是一个矩阵是A矩阵称为分块矩阵,在性质满足的前提下依然满足矩阵加法乘法。 例如矩阵乘法A×B,将B按行分块,可以看成矩阵A乘列向量,其中B中每个元素是一个行向量;将A按列分块同理。
简单地说,就是矩阵里的元素还是个矩阵。这道题我们可以像这样构建矩阵:
∵Sn=Sn-1+Ak ∴有如下转移图

写出邻接矩阵 (下图用E表示单位矩阵 也就是"1”,0表示全是0的矩阵 也就是“0”,A即为输入的矩阵)

也就有:




最终答案是:


所以,最终C++程序只需要重载运算符就可以轻松AC了

而另一种做法,也就是二分加矩阵快速幂则需要较长时间(800+MS)

#include <iostream>
#include <algorithm>
#include <cmath>
#include <ctime>
#include <cstring>
#include <cstdio>
#include <cstdlib> using namespace std; int n,k,m; class Matrix
{
public:
int val[][];
int x,y; Matrix()
{
memset(val,,sizeof(val));
x=y=;
return ;
} void set_E()
{
int i;
for(i=;i<=x;++i)
val[i][i]=;
return ;
} Matrix operator*(Matrix b)
{
int i,j,k;
Matrix c;
c.resize(x,b.y); for(k=;k<=b.x;++k)
for(i=;i<=x;++i)
if(val[i][k])//不加这行就要340+MS
for(j=;j<=b.y;++j)
c.val[i][j]=(c.val[i][j]+val[i][k]*b.val[k][j])%m;
return c;
} Matrix operator+(Matrix b)
{
Matrix c;
c.resize(max(x,b.x),max(y,b.y));
int i,j; for(i=;i<=c.x;++i)
for(j=;j<=c.y;++j)
c.val[i][j]=(val[i][j]+b.val[i][j])%m; return c;
} void resize(const int & _x,const int & _y)
{
x=_x,y=_y;
return ;
}
}A; class Matrix_Plus
{
public:
Matrix val[][];
int x,y; Matrix_Plus()
{
memset(val,,sizeof(val));
x=y=;
return ;
} void set_E()
{
int i;
for(i=;i<=x;++i)
val[i][i].set_E();
return ;
} Matrix_Plus operator*(Matrix_Plus b)
{
Matrix_Plus c;
int i,j,k;
c.resize(x,b.y); for(k=;k<=b.x;++k)
for(i=;i<=x;++i)
for(j=;j<=b.y;++j)
c.val[i][j]=c.val[i][j]+val[i][k]*b.val[k][j];
return c;
} Matrix_Plus operator^(int p)
{
Matrix_Plus r,base;
r.resize(,);
r.val[][].resize(n,n);
r.val[][].resize(n,n);
r.val[][].resize(n,n);
r.val[][].resize(n,n);
r.set_E();
base=*this; while(p)
{
if(p&)
r=r*base;
base=base*base;
p>>=;
} return r;
} void resize(const int & _x,const int & _y)
{
x=_x,y=_y;
return ;
} }S,A_; int main()
{
int i,j; scanf("%d%d%d",&n,&k,&m);
A.resize(n,n); for(i=;i<=n;++i)
{
for(j=;j<=n;++j)
{
scanf("%d",&A.val[i][j]);
}
} S.resize(,);
S.val[][]=A;
S.val[][].resize(n,n);
S.val[][].resize(n,n); A_.resize(,);
A_.val[][].resize(n,n);
A_.val[][].resize(n,n);
A_.val[][].resize(n,n);
A_.val[][].resize(n,n);
A_.val[][].set_E();
A_.val[][].set_E();
A_.val[][]=A;
S=S*(A_^k); for(i=;i<=n;++i)
{
for(j=;j<=n;++j)
printf("%d ",S.val[][].val[i][j]);
printf("\n");
}
return ;
}
poj3233 题解 矩阵乘法 矩阵快速幂的更多相关文章
- Luogu 3390 【模板】矩阵快速幂 (矩阵乘法,快速幂)
Luogu 3390 [模板]矩阵快速幂 (矩阵乘法,快速幂) Description 给定n*n的矩阵A,求A^k Input 第一行,n,k 第2至n+1行,每行n个数,第i+1行第j个数表示矩阵 ...
- Luogu T7152 细胞(递推,矩阵乘法,快速幂)
Luogu T7152 细胞(递推,矩阵乘法,快速幂) Description 小 X 在上完生物课后对细胞的分裂产生了浓厚的兴趣.于是他决定做实验并 观察细胞分裂的规律. 他选取了一种特别的细胞,每 ...
- HDU4965 Fast Matrix Calculation —— 矩阵乘法、快速幂
题目链接:https://vjudge.net/problem/HDU-4965 Fast Matrix Calculation Time Limit: 2000/1000 MS (Java/Othe ...
- bzoj 3240: [Noi2013]矩阵游戏 矩阵乘法+十进制快速幂+常数优化
3240: [Noi2013]矩阵游戏 Time Limit: 10 Sec Memory Limit: 256 MBSubmit: 613 Solved: 256[Submit][Status] ...
- poj3613:Cow Relays(倍增优化+矩阵乘法floyd+快速幂)
Cow Relays Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 7825 Accepted: 3068 Descri ...
- BZOJ_1009_[HNOI2008]_GT考试_(动态规划+kmp+矩阵乘法优化+快速幂)
描述 http://www.lydsy.com/JudgeOnline/problem.php?id=1009 字符串全部由0~9组成,给出一个串s,求一个长度为n的串,不包含s的种类有多少. 分析 ...
- bzoj 3240 矩阵乘法+十进制快速幂
首先,构造出从f[][i]->f[][i+1]的转移矩阵a,和从f[i][m]->f[i+1][1]的转移矩阵b, 那么从f[1][1]转移到f[n][m]就是init*(a^(m-1)* ...
- 【HDOJ5950】Recursive sequence(矩阵乘法,快速幂)
题意:f[1]=a,f[2]=b,f[i]=2f[i-2]+f[i-1]+i^4(i>=3),多组询问求f[n]对2147493647取模 N,a,b < 2^31 思路:重点在于i^4的 ...
- 数学--数论--HDU 4675 GCD of Sequence(莫比乌斯反演+卢卡斯定理求组合数+乘法逆元+快速幂取模)
先放知识点: 莫比乌斯反演 卢卡斯定理求组合数 乘法逆元 快速幂取模 GCD of Sequence Alice is playing a game with Bob. Alice shows N i ...
随机推荐
- markdownpad2下载安装教程
1.下载安装 http://markdownpad.com/download/markdownpad2-setup.exe 直接下载,安装过程中提醒要安装微软的一个什么环境,不用理会直接跳过,实测没有 ...
- sql 查询出当天记录数据
select updatetime,NewComment,HistoryID,sum(1) over(partition by UpdateTime) from LPProjectHistoryord ...
- HttpPostedFileBase 基类
public void uploadDocMentSave(string Type) { if (Request.Files.Count > 0) { Htt ...
- Ubuntu下搭建repo服务器(二): 配置git-daemon-run
git-daemon-run实际是一个脚本管理工具,用来启动git-daemon. 1 安装git-daemon-run(A端) apt-get install git-daemon-run 2. 配 ...
- Java系列学习(十二)-开始Eclipse
1.用Eclipse来写一个HelloWorld (1)选择工作空间 工作空间其实就是我们写的源代码所在的目录 (2)创建一个Java项目 [File-New-Java Project] (3)创建包 ...
- Android热修复方案比较
热修复的特点:无需重新发版,实时高效热修复:用户无感知修复,无需下载新的应用,代价小: 修复成功率高,把损失降到最低. 一.热修复开源方案和使用情况 方案名称 方案开发公司 开发时间 Github星评 ...
- Mac下CUDA开启及Tensorflow-gpu 1.4 安装
本文由@ray 出品,转载请注明出处. 文章链接:http://www.cnblogs.com/wolfray/p/8040694.html 在之前的文章中,笔者介绍了在Mac下安装Tensorfl ...
- linux shell & bash
shell & bash shell指允许用户通过文本操作计算机的程序. interactive shell:从是否通过标准输入输出与用户进行交互的角度分为交互式shell(interacti ...
- 4.用Redis Desktop Manager连接Redis(Windows)
相比连接CentOS的Redis,在Windows中的操作简单得让人感动. 所以这里我们使用的服务器系统是Windows Server 2016 R2. 而Windows版本的Redis官方网站并没有 ...
- hdu,1028,整数拆分的理解
#include"iostream"using namespace std;int main() { int n,i,j,k; int c[122],temp[122]; //c[ ...