• poj 3233 矩阵快速幂


    地址 http://poj.org/problem?id=3233

    大意是n维数组 最多k次方  结果模m的相加和是多少

    Given a n × n matrix A and a positive integer k, find the sum S = A + A2 + A3 + … + Ak.

    Sample Input

    2 2 4
    0 1
    1 1

    Sample Output

    1 2
    2 3

    题解

    矩阵逐步的相乘然后相加是不可以 但是矩阵也有类似快速幂的做法

    /*
    A + A^2 =A(I+A)

    A + A^2 + A^3 + A^4 = (A + A^2)(I + A^2)
    记做sum(n) = A +A^2 +A^3 +...+A^n
    如果n是偶数 sum(n) = sum(n/2)(I+A^(n/2))
    如果n是奇数 sum(n) = sum(n-1) + A^n
    = sum((n-1)/2)(I+A^((n-1)/2)) + A^n
    */

    代码如下

      1 #include <iostream>
      2 #include <cstring>
      3 
      4 using namespace std;
      5 
      6 
      7 struct matrix {
      8     int data[35][35];
      9 };
     10 
     11 int n = 0;
     12 int m = 0;
     13 int k = 0;
     14 
     15 //矩阵乘法
     16 matrix mul(matrix a, matrix b)
     17 {
     18     matrix c;
     19     memset(c.data, 0, sizeof(c.data));
     20     for (int i = 1; i <= n; i++) {
     21         for (int j = 1; j <= n; j++) {
     22             for (int k = 1; k <= n; k++) {
     23                 c.data[i][j] = (c.data[i][j] + 1ll * a.data[i][k] * b.data[k][j]) % m;
     24             }
     25         }
     26     }
     27 
     28     return c;
     29 }
     30 
     31 //矩阵加法
     32 matrix add(matrix a, matrix b) {
     33     for (int i = 1; i <= n; i++) {
     34         for (int j = 1; j <= n; j++) {
     35             a.data[i][j] = (a.data[i][j] + b.data[i][j])%m;
     36         }
     37     }
     38     return a;
     39 }
     40 
     41 //矩阵快速幂
     42 matrix quickpow(matrix a, int k) {
     43     matrix  c;
     44     memset(c.data, 0, sizeof(c.data));
     45     for (int i = 1; i <= n; i++)
     46         c.data[i][i] = 1;
     47     while (k) {
     48         if (k & 1) c = mul(c, a);
     49         k >>= 1;
     50         a = mul(a, a);
     51     }
     52     return c;
     53 }
     54 
     55 //正式计算 sum k
     56 matrix sum(matrix a, int k) {
     57     if (k == 1) return a;
     58     matrix c;
     59     memset(c.data, 0, sizeof(c.data));
     60     for (int i = 1; i <= n; i++)
     61         c.data[i][i] = 1;
     62     c = add(c, quickpow(a, k >> 1));
     63     c = mul(c, sum(a, k >> 1));
     64     if (k & 1) c = add(c, quickpow(a, k));
     65     return c;
     66 }
     67 
     68 
     69 
     70 
     71 /*
     72 A + A^2 =A(I+A)
     73 
     74 A  + A^2 + A^3 + A^4 = (A + A^2)(I + A^2)
     75 记做sum(n) = A  +A^2 +A^3 +...+A^n
     76 如果n是偶数  sum(n) = sum(n/2)(I+A^(n/2))
     77 如果n是奇数  sum(n) = sum(n-1) + A^n
     78             = sum((n-1)/2)(I+A^((n-1)/2)) + A^n
     79 */
     80 
     81 int main()
     82 {
     83     matrix mat;
     84     cin >> n;
     85     cin >> k;
     86     cin >> m;
     87 
     88     for (int i = 1; i <= n; i++) {
     89         for (int j = 1; j <= n; j++) {
     90             cin >> mat.data[i][j];
     91         }
     92     }
     93 
     94     matrix ret = sum(mat, k);
     95 
     96     
     97 
     98     for (int i = 1; i <= n; i++) {
     99         for (int j = 1; j <= n; j++) {
    100             cout << ret.data[i][j] << " ";
    101         }
    102         cout << endl;
    103     }
    104 }
    View Code
    作 者: itdef
    欢迎转帖 请保持文本完整并注明出处
    技术博客 http://www.cnblogs.com/itdef/
    B站算法视频题解
    https://space.bilibili.com/18508846
    qq 151435887
    gitee https://gitee.com/def/
    欢迎c c++ 算法爱好者 windows驱动爱好者 服务器程序员沟通交流
    如果觉得不错,欢迎点赞,你的鼓励就是我的动力
    阿里打赏 微信打赏
  • 相关阅读:
    pwnable
    pwnable
    pwnable
    uva 11971
    uva 11582
    【数据结构】关于递归的几个例子
    【数据结构】快速排序
    【Python】range 倒序
    【数据结构】静态链表的实现(C语言描述)
    【数据结构】KMP 算法
  • 原文地址:https://www.cnblogs.com/itdef/p/11989353.html
Copyright © 2020-2023  润新知