UVa 11149 Power of Matrix (矩阵快速幂,倍增法或构造矩阵)
题意:求A + A^2 + A^3 + ... + A^m。
析:主要是两种方式,第一种是倍增法,把A + A^2 + A^3 + ... + A^m,拆成两部分,一部分是(E + A^(m/2))(A + A^2 + A^3 + ... + A^(m/2)),然后依次计算下去,就可以分解,logn的复杂度分解,注意要分奇偶。
另一种是直接构造矩阵,
,然后就可以用辞阵快速幂计算了,注意要用分块矩阵的乘法。
代码如下:
倍增法:
#pragma comment(linker, "/STACK:1024000000,1024000000")
#include <cstdio>
#include <string>
#include <cstdlib>
#include <cmath>
#include <iostream>
#include <cstring>
#include <set>
#include <queue>
#include <algorithm>
#include <vector>
#include <map>
#include <cctype>
#include <cmath>
#include <stack>
#include <sstream>
#include <list>
#define debug() puts("++++");
#define gcd(a, b) __gcd(a, b)
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define freopenr freopen("in.txt", "r", stdin)
#define freopenw freopen("out.txt", "w", stdout)
using namespace std; typedef long long LL;
typedef unsigned long long ULL;
typedef pair<int, int> P;
const int INF = 0x3f3f3f3f;
const double inf = 0x3f3f3f3f3f3f;
const double PI = acos(-1.0);
const double eps = 1e-8;
const int maxn = 1e3 + 10;
const int mod = 10;
const int dr[] = {-1, 0, 1, 0};
const int dc[] = {0, 1, 0, -1};
const char *de[] = {"0000", "0001", "0010", "0011", "0100", "0101", "0110", "0111", "1000", "1001", "1010", "1011", "1100", "1101", "1110", "1111"};
int n, m;
const int mon[] = {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
const int monn[] = {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
inline bool is_in(int r, int c) {
return r > 0 && r <= n && c > 0 && c <= m;
} struct Matrix{
int a[40][40];
int n; friend Matrix operator + (const Matrix &lhs, const Matrix &rhs){
Matrix res;
res.n = lhs.n;
for(int i = 0; i < lhs.n; ++i)
for(int j = 0; j < lhs.n; ++j)
res.a[i][j] = (lhs.a[i][j] + rhs.a[i][j]) % mod;
return res;
} friend Matrix operator * (const Matrix &lhs, const Matrix &rhs){
Matrix res;
res.n = lhs.n;
for(int i = 0; i < lhs.n; ++i)
for(int j = 0; j < lhs.n; ++j){
res.a[i][j] = 0;
for(int k = 0; k < lhs.n; ++k)
res.a[i][j] += lhs.a[i][k] * rhs.a[k][j];
res.a[i][j] %= mod;
}
return res;
}
}; Matrix E; Matrix fast_pow(Matrix a, int m){
Matrix res;
res.n = n;
memset(res.a, 0, sizeof res.a);
for(int i = 0; i < res.n; ++i)
res.a[i][i] = 1;
while(m){
if(m & 1) res = res * a;
m >>= 1;
a = a * a;
}
return res;
} Matrix dfs(int m, Matrix x){
if(m == 1) return x;
if(m == 0) return E;
Matrix ans = (E + fast_pow(x, m/2)) * dfs(m/2, x);
if(m & 1) ans = ans + fast_pow(x, m);
return ans;
} int main(){
while(scanf("%d %d", &n, &m) == 2 && n){
Matrix x; x.n = n;
E.n = n;
memset(E.a, 0, sizeof E.a);
for(int i = 0; i < n; ++i)
E.a[i][i] = 1;
for(int i = 0; i < n; ++i)
for(int j = 0; j < n; ++j){
scanf("%d", &x.a[i][j]);
x.a[i][j] %= mod;
} Matrix ans = dfs(m, x);
for(int i = 0; i < n; ++i)
for(int j = 0; j < n; ++j)
if(j + 1 == n) printf("%d\n", ans.a[i][j]);
else printf("%d ", ans.a[i][j]);
printf("\n");
}
return 0;
}
构造法:
#pragma comment(linker, "/STACK:1024000000,1024000000")
#include <cstdio>
#include <string>
#include <cstdlib>
#include <cmath>
#include <iostream>
#include <cstring>
#include <set>
#include <queue>
#include <algorithm>
#include <vector>
#include <map>
#include <cctype>
#include <cmath>
#include <stack>
#include <sstream>
#include <list>
#define debug() puts("++++");
#define gcd(a, b) __gcd(a, b)
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define freopenr freopen("in.txt", "r", stdin)
#define freopenw freopen("out.txt", "w", stdout)
using namespace std; typedef long long LL;
typedef unsigned long long ULL;
typedef pair<int, int> P;
const int INF = 0x3f3f3f3f;
const double inf = 0x3f3f3f3f3f3f;
const double PI = acos(-1.0);
const double eps = 1e-8;
const int maxn = 1e3 + 10;
const int mod = 10;
const int dr[] = {-1, 0, 1, 0};
const int dc[] = {0, 1, 0, -1};
const char *de[] = {"0000", "0001", "0010", "0011", "0100", "0101", "0110", "0111", "1000", "1001", "1010", "1011", "1100", "1101", "1110", "1111"};
int n, m;
const int mon[] = {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
const int monn[] = {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
inline bool is_in(int r, int c) {
return r > 0 && r <= n && c > 0 && c <= m;
} struct Node{
int a[80][80]; friend void add(const Node &lhs, const Node &rhs, Node &res, int x, int y, int l, int r){
for(int i = x; i < y; ++i)
for(int j = l; j < r; ++j)
res.a[i][j] = (lhs.a[i-x][j-l] + rhs.a[i-x][j-l]) % mod;
} friend void solve(int x, int y, int l, int r, int p, int q, const Node &lhs, const Node &rhs, Node &res){
for(int i = x; i < y; ++i)
for(int j = l; j < r; ++j){
res.a[i-x][j-l] = 0;
for(int k = p; k < q; ++k)
res.a[i-x][j-l] += lhs.a[i][k] * rhs.a[k][j];
}
} friend Node operator * (const Node &lhs, const Node &rhs){
Node res, x, y;
solve(0, n, 0, n, 0, n, lhs, rhs, x);
solve(0, n, 0, n, n, n+n, lhs, rhs, y);
add(x, y, res, 0, n, 0, n); solve(0, n, n, n+n, 0, n, lhs, rhs, x);
solve(0, n, n, n+n, n, n+n, lhs, rhs, y);
add(x, y, res, 0, n, n, n+n); solve(n, n+n, 0, n, 0, n, lhs, rhs, x);
solve(n, n+n, 0, n, n, n+n, lhs, rhs, y);
add(x, y, res, n, n+n, 0, n); solve(n, n+n, n, n+n, 0, n, lhs, rhs, x);
solve(n, n+n, n, n+n, n, n+n, lhs, rhs, y);
add(x, y, res, n, n+n, n, n+n); return res;
}
}; Node fast_pow(Node a, int m){
Node res;
memset(res.a, 0, sizeof res.a);
for(int i = 0; i < n; ++i)
res.a[i][i] = res.a[i+n][i] = 1; while(m){
if(m & 1) res = res * a;
m >>= 1;
a = a * a;
}
return res;
} int main(){
while(scanf("%d %d", &n, &m) == 2 && n){
Node x, y;
memset(y.a, 0, sizeof y.a);
for(int i = 0; i < n; ++i)
for(int j = n; j < n+n; ++j){
scanf("%d", &y.a[i][j]);
y.a[i][j] %= mod;
}
for(int i = 0; i < n; ++i)
y.a[i][i] = 1;
for(int i = n; i < n + n; ++i)
for(int j = n; j < n + n; ++j)
y.a[i][j] = y.a[i-n][j];
memset(x.a, 0, sizeof x.a);
for(int i = n; i < n+n; ++i)
x.a[i][i-n] = 1; Node ans = fast_pow(y, m); if(m) ans = ans * x;
for(int i = 0; i < n; ++i)
for(int j = 0; j < n; ++j)
if(j == n-1) printf("%d\n", ans.a[i][j]);
else printf("%d ", ans.a[i][j]);
printf("\n");
}
return 0;
}
UVa 11149 Power of Matrix (矩阵快速幂,倍增法或构造矩阵)的更多相关文章
- UVA 11149.Power of Matrix-矩阵快速幂倍增
Power of Matrix UVA - 11149 代码: #include <cstdio> #include <cstring> #include < ...
- UVA - 11149 (矩阵快速幂+倍增法)
第一道矩阵快速幂的题:模板题: #include<stack> #include<queue> #include<cmath> #include<cstdio ...
- UVA 11149 - Power of Matrix(矩阵乘法)
UVA 11149 - Power of Matrix 题目链接 题意:给定一个n*n的矩阵A和k,求∑kiAi 思路:利用倍增去搞.∑kiAi=(1+Ak/2)∑k/2iAi,不断二分就可以 代码: ...
- BZOJ.4180.字符串计数(后缀自动机 二分 矩阵快速幂/倍增Floyd)
题目链接 先考虑 假设S确定,使构造S操作次数最小的方案应是:对T建SAM,S在SAM上匹配,如果有S的转移就转移,否则操作数++,回到根节点继续匹配S.即每次操作一定是一次极大匹配. 简单证明:假设 ...
- UVA 11149 Power of Matrix
矩阵快速幂. 读入A矩阵之后,马上对A矩阵每一个元素%10,否则会WA..... #include<cstdio> #include<cstring> #include< ...
- Luogu P3390 【模板】矩阵快速幂&&P1939 【模板】矩阵加速(数列)
补一补之前的坑 因为上次关于矩阵的那篇blog写的内容太多太宽泛了,所以这次把一些板子和基本思路理一理 先看这道模板题:P3390 [模板]矩阵快速幂 首先我们知道矩阵乘法满足结合律而不满足交换律的一 ...
- 2019 牛客暑期多校 B generator 1 (矩阵快速幂+倍增)
题目:https://ac.nowcoder.com/acm/contest/885/B 题意:给你x0,x1,让你求出xn,递推式时xn=a*xn-1+b*xn-2 思路:这个n特别大,我自己没有摸 ...
- UVa 11149 Power of Matrix(倍增法、矩阵快速幂)
题目链接: 传送门 Power of Matrix Time Limit: 3000MS Description 给一个n阶方阵,求A1+A2+A3+......Ak. 思路 A1+A2+. ...
- UVA 11149 Power of Matrix 快速幂
题目链接: http://acm.hust.edu.cn/vjudge/contest/122094#problem/G Power of Matrix Time Limit:3000MSMemory ...
随机推荐
- Linux环境安装redis
redis官网地址:http://www.redis.io/ 最新版本:2.8.3 在Linux下安装Redis非常简单,具体步骤如下(官网有说明): 1.下载源码,解压缩后编译源码. $ wget ...
- HttpClient超时设置
场景:最近并发较高,看到响应时间6s的时候,心里咯噔一下,我记得我设置的超时时间是5s啊. 原来读取超时时间没生效,只生效了连接超时时间. ConnectionPoolTimeoutExcepti ...
- Linux环境抓包命令
有时候有些接口调用问题不好定位或者日志不够详细,那么我们往往会选择通过抓包来看详细的通讯过程.抓包有相关软件,这里说如何直接在环境里抓.假如现在我们在 Linux 下部署了 Tomcat 服务器,端口 ...
- 借助curl理解$GLOBALS['HTTP_RAW_POST_DATA'] ,$_POST, php://input
发送请求代码 post.php <?php $url='http://localhost/web/curl/url.php'; $data='a=123|b=2&c=3'; $heade ...
- FTP,FTPS,FTPS与防火墙
昨天搭建了一台FTPS服务器,过程中学习了很多不清楚的知识点,还有遇到的问题,记录一下. (大部分内容汇集.整理自网络) 一. 关于FTP传输模式 众所周知,FTP传输有两种工作模式,Active M ...
- Jenkins详细安装教程
1.先下载msi文件 Jenkins下载链接: https://pan.baidu.com/s/1SACKNgW7OZrJoXMRDhsJxQ 提取码: 94b9 2.安装 解压后得到的是jenkin ...
- xunsearch全文检索初体验
目录 测试添加数据 测试搜索 简单搜索 稍微复杂的搜索 搜索建议 测试添加数据 ./Indexer.php --source=csv --clean demo 清空现有索引数据 ... 初始化数据源 ...
- php读取文件夹文件,清理文件
// 获取文件夹中图片的数量和名称 public function show_tmp_file() { $handler = opendir('./tmp/');//当前目录中的文件夹下的文件夹 $c ...
- tomcat7.0在centos7下中文乱码问题解决汇总
1. 系统级的中文设置 Centos7跟之前的6和5安装的中文字符命令都不一样 [root@iZ25bdzgev8Z ~]# locale #查看当前系统的语言环境 [root@iZ25bdzgev8 ...
- Cassandra学习六 一些知识点
http://www.flyml.net/2016/09/08/cassandra-tutorial-java-api-example/ Cassandra对查询的支持很弱,只支持主键列及索引列的查询 ...