您的位置:首页 > 其它

POJ 3735 构造矩阵乘法

2012-03-31 22:28 363 查看
看来还是要吧这个矩阵乘法理解透啊!

我的题解大体和网上的一样吧。没有什么可取性。

对于矩阵,我们熟悉的操作有两种,交换与置零。

我们有初始的矩阵T[ A,B,C,D ];

交换矩阵为

                       | 1 0 0 0 |       

[b][ A,B,C,D ]  X  | 0 0 1 0 |  =>[ A C B D ][/b]

                       | 0 1 0 0 |       

                       | 0 0 0 1 |

置零矩阵为

                       | 1 0 0 0 |       
[b][ A,B,C,D ]  X  | 0 1 0 0 |  =>[ A B 0 D ][/b]
                       | 0 0 0 0 |       
                       | 0 0 0 1 |
接下来的问题就是+1 操作了

                       | 1 1 0 0 |       

[b][ 1,B,C,D ]  X  | 0 1 0 0 |  =>[ 1,B+1,C,D ][/b]

                       | 0 0 1 0 |       

                       | 0 0 0 1 |

然后用矩阵的快速幂就可以了。
#include<iostream>
#include<string.h>
#include<cstdio>
#define MAXN 111
using namespace std;

typedef long long ll;
int n,m,k;
struct node{
ll ma[MAXN][MAXN];
};

node matrix,res;

node matriXmult( node a,node b )
{
node c;
memset( c.ma,0,sizeof(c.ma) );
for( int i=0;i<=n;i++ )
for( int k=0;k<=n;k++ )
if( a.ma[i][k] )
for( int j=0;j<=n;j++ )
c.ma[i][j]+=a.ma[i][k]*b.ma[k][j];
return c;
}

int main()
{
while( scanf("%d%d%d",&n,&m,&k)&&n|k|m )
{
memset( matrix.ma,0,sizeof(matrix.ma) );
for( int i=0;i<=n;i++ )
matrix.ma[i][i]=1;
while( k-- )
{
char command;
int x,y;
scanf( "\n%c",&command );
if( command=='g' ){
scanf( "%d",&x );
matrix.ma[0][x]++;
}
else if( command=='e' ){
scanf( "%d",&x );
for( int i=0;i<=n;i++ )
matrix.ma[i][x]=0;
}
else if( command=='s' ){
scanf( "%d %d",&x,&y );
for( int i=0;i<=n;i++ )
swap( matrix.ma[i][x],matrix.ma[i][y] );
}
}
memset( res.ma,0,sizeof(res.ma) );
for( int i=0;i<=n;i++ )
res.ma[i][i]=1;
for( int i=0;i<31;i++ ){
if( m&(1<<i) )
res=matriXmult( res,matrix );
matrix=matriXmult( matrix,matrix );
}
printf( "%I64d",res.ma[0][1] );
for( int i=2;i<=n;i++ )
printf( " %I64d",res.ma[0][i] );
putchar('\n');
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  matrix command c