//-------矩阵的乘法--------- /* 假设题目: 3 0 0 5 0 2 0 6 M= 0 -1 0 0 N= 1 0 Q=-1 0 Q=M*N 2 0 0 0 -2 4 0 4 0 0 (表1) 非零元三元表: M: N: Q: i表示行 j表示列 e表示非零元的数据 ---------- ---------- ---------- i j e i j e i j e ---------- ---------- ---------- 1 1 3 1 2 2 1 2 6 1 4 5 2 1 1 2 1 -1 2 2 -1 3 1 -2 3 2 4 3 1 2 3 2 4 (表2) rpos表(各行第一个非零元位置): M: N: Q: row表示行 rpos表示每行第一个非零元是第几个非零元 ---------------- -------------------- ------------- row 1 2 3 row 1 2 3 4 row 1 2 3 ---------------- -------------------- ------------- rpos 1 3 4 rpos 1 2 3 5 rpos 1 2 3 (表3) n1 ∑M(i,k)*N(k,j) 1=<i<=m1 1=<j<=n2 //矩阵求积公式 k=1 */ #include<stdio.h> #include<stdlib.h> //宏定义 #define MAXSIZE 4 #define MAXRC 4 #define ERROR 0 #define OK 1 typedef int Status; typedef struct { int i,j; //i,j表示行与列 int e; //e表示在该位置的数据 }Triple; //三元组模拟表1 typedef struct { Triple date[MAXSIZE+1]; //非零三元组表 int rops[MAXRC+1]; //各行的第一个非零元 int mu,nu,tu; //矩阵的行,列,非零元的个数 }RLSMatrix; //矩阵的抽象 Status MultSMatrix(RLSMatrix M,RLSMatrix N,RLSMatrix *Q);//计算矩阵乘积的函数 void main() { RLSMatrix M,N,Q; int k; M.date[1].i=1; M.date[1].j=1; M.date[1].e=3; M.date[2].i=1; M.date[2].j=4; M.date[2].e=5; M.date[3].i=2; M.date[3].j=2; M.date[3].e=-1; M.date[4].i=3; M.date[4].j=1; M.date[4].e=2; M.rops[1]=1; M.rops[2]=2; M.rops[3]=4; M.mu=3; M.nu=4; M.tu=4; //初始化M矩阵的各项属性 N.date[1].i=1; N.date[1].j=2; N.date[1].e=2; N.date[2].i=2; N.date[2].j=1; N.date[2].e=1; N.date[3].i=3; N.date[3].j=1; N.date[3].e=-2; N.date[4].i=3; N.date[4].j=2; N.date[4].e=4; N.rops[1]=1; N.rops[2]=2; N.rops[3]=3; N.rops[4]=5; N.mu=4; N.nu=2; N.tu=4; //初始化N矩阵的各项矩阵 MultSMatrix(M,N,&Q); printf("Q:\n-------------------\ni\tj\te\n-------------------\n"); for(k=1;k<=Q.tu;k++) { printf("%d\t%d\t%d\n",Q.date[k].i,Q.date[k].j,Q.date[k].e); } getchar(); getchar(); } Status MultSMatrix(RLSMatrix M,RLSMatrix N,RLSMatrix *Q) { int arow,ccol,ctemp[4]; //Q矩阵的行,列,以及乘积的累加 int tp,p,q,t,i,brow; //需要用到的中间量 Q->mu=M.mu; Q->nu=N.nu; Q->tu=0; //Q矩阵的初始化 if(M.nu!=N.mu) { return ERROR; //根据矩阵的性质判断两个矩阵能否相乘,如不能返回ERROR } if(0!=M.tu*N.tu) //判断Q是否为0矩阵,不是则继续 { for(arow=1;arow<=M.mu;arow++) { for(i=0;i<4;i++) { ctemp[i]=0; //初始化累加器,用于存M的某个行元素与N的整列元素的乘积和(参考矩阵的乘法) } Q->rops[arow]=Q->tu+1; //生成Q的rops表(参考表3,用于方便的定位和计算) if(arow<M.mu) { tp=M.rops[arow+1]; //tp定位到要累乘行的下一行 } else { tp=M.tu+1; } for(p=M.rops[arow];p<tp;p++) //遍历第arow行的矩阵元素 { brow=M.date[p].j; //∑M(i,k)*N(k,j) M的矩阵的列和N矩阵的行相同. if(brow<N.mu) { t=N.rops[brow+1]; } else { t=N.tu+1; //原理同M矩阵的搜寻一样 } for(q=N.rops[brow];q<t;q++) { ccol=N.date[q].j; ctemp[ccol]+=M.date[p].e*N.date[q].e; //乘积和 } } for(ccol=1;ccol<=Q->nu;ccol++) { if(ctemp[ccol]) { if(++Q->tu>MAXSIZE) { return ERROR; //检查是否溢出 } Q->date[Q->tu].i=arow; Q->date[Q->tu].j=ccol; Q->date[Q->tu].e=ctemp[ccol]; } } } } return OK; }