POJ-3233 Matrix Power Series

来源:互联网 发布:json 数字 不带双引号 编辑:程序博客网 时间:2024/06/13 03:59

原题链接:http://poj.org/problem?id=3233

这一题是求S=A+A^2+....+A^K的和矩阵(二分再二分)

贴我的矩阵快速幂(二分思想)模板链接:http://blog.csdn.net/x_xueting/article/details/77507566

然后就是求和的二分

                 举个例子当k=6时  A+A^2+A^3+A^4+A^5+A^6=(A^1+A^2+A^3)+(A^1+A^2+A^3)*A^3

                                 K=5时 A+A^2+A^3+A^4+A^5=(A+A^2)+(A+A^2)*A^3+A^3

                 这就是二分的思想

当k为偶数时: A^1+A^2+...+A^K=(A^1+A^2+...+A^(K/2))+(A^1+A^2+...+A^(K/2))*A^(K/2)

                  F(k)=F(k/2)+F(k/2)*A^(K/2)

当k为奇数时:A^1+A^2+...+A^K=(A^1+A^2+...+A^(K/2))+(A^1+A^2+...+A^(K/2))*A^(K/2+1)+A^(K/2+1)

                 F(k)=F(k/2)+F(k/2)*A^(k/2+1)+A^(k/2+1)(利用递归去求)

代码

#include <iostream>
#include <cstdio>
#include <cstring>
#define ll long long int
using namespace std;
int n;
ll m,k;
typedef struct mar
{
    ll matrix[31][31];
} Mar;


void print(Mar a)
{
    for(int i=0; i<n; i++)
    {
        for(int j=0; j<n; j++)
            cout<<a.matrix[i][j]%m<<" ";
        cout<<endl;
    }
}
Mar mul(Mar a,Mar b)
{
    Mar temp;
    for(int i=0; i<n; i++)
    {
        for(int j=0; j<n; j++)
        {
            temp.matrix[i][j]=0;
            for(int t=0; t<n; t++)
            {
                temp.matrix[i][j]+=(a.matrix[i][t]*b.matrix[t][j])%m;
            }
            temp.matrix[i][j]%=m;
        }
    }
    return temp;
}
Mar power(Mar mar,ll r)
{
    Mar mt;
    memset(mt.matrix,0,sizeof(mt.matrix));
    for(int i=0; i<n; i++)
        mt.matrix[i][i]=1;
    while(r)
    {
        if(r&1)
              mt=mul(mar,mt);
        mar=mul(mar,mar);
        r=r/2;
    }
    return mt;
}
Mar Add(Mar a,Mar b)
{
    Mar temp;
    for(int i=0; i<n; i++)
    {
        for(int j=0; j<n; j++)
        {
            temp.matrix[i][j]=a.matrix[i][j]+b.matrix[i][j];
            temp.matrix[i][j]%=m;
        }
    }
    return temp;
}
Mar c;
Mar F(ll s)
{
    if(s==1)
        return c;
    else
    {
        Mar res=F(s/2);
        if(s%2)
        {
            Mar cur=power(c,s/2+1);
            res=Add(Add(res,cur),mul(cur,res));
            return res;
        }
        else
        {
           Mar cur=power(c,s/2);
           res=Add(res,mul(cur,res));
           return res;
        }
    }




}
int main()
{
    while(cin>>n>>k>>m)
    {
        for(int i=0; i<n; i++)
            for(int j=0; j<n; j++)
                cin>>c.matrix[i][j];
        c=F(k);
        print(c);
    }
    return 0;
}

原创粉丝点击