稀疏矩阵相乘的问题

//DEV开发环境 ,稀疏矩阵三元组表示
//作者:赵自明
//其中乘法代码参考严蔚敏数据结构
//开发完成日期:07年11月8日
//测试环境:window xp,vista
#include <cstdlib>
#include <iostream>
#define MAXSIZE 100
#define MAXRC 50
using namespace std;
typedef int ElemType;
typedef struct{
int i,j;//非零元在矩阵中的真实位置
ElemType e;//非零元
}Triple;//定义存放非零元素的结构体

typedef struct{
Triple data[MAXSIZE+1];//在使用过程有效位置也是从下标1开始
int mu,nu,tu;//行,列,非零元个数
int rpos[MAXRC+1];//从下标为1的位置开始存放每一行的第一个元素对应的在data中的位置
}TSMatrix;//定义存放稀疏矩阵的数据类型

int
MultSMatrix(const TSMatrix &M ,const TSMatrix &N,TSMatrix &Q)
//两个稀疏矩阵相乘,由于不改变M,N,结果存放到Q中,所以给M,N参数加CONST限定
{
if(M.nu!=N.mu)
{printf("M.nu!=N.mu\n");
return 0;}

Q.mu=M.mu; Q.nu=N.nu; Q.tu=0;
if(M.tu*N.tu){
int arow;
int ctemp[N.nu+1];////////这里能这样定义吗????????????
for(arow=1;arow<=M.mu;++arow)
{ int i;
for(i=1;i<=N.nu;i++)ctemp[i]=0;//////////这啥意思呢???????????
Q.rpos[arow]=Q.tu+1;///////////还有这里???????

int tp;
if(arow<M.mu)tp=M.rpos[arow+1];
else{tp=M.tu+1;}

int brow,t,ccol,p;
for(p=M.rpos[arow];p<tp;++p)
{ brow=M.data[p].j;
if(brow<N.mu)t=N.rpos[brow+1];
else {t=N.tu+1;}
int q;
for(q=N.rpos[brow];q<t;++q)
{ccol=N.data[q].j;
ctemp[ccol]+=M.data[p].e*N.data[q].e;

}
}

for(ccol=1;ccol<=Q.nu;++ccol)
if(ctemp[ccol]){if(++Q.tu>MAXSIZE)return 0;

Q.data[Q.tu].i=arow;
Q.data[Q.tu].j=ccol;
Q.data[Q.tu].e=ctemp[ccol];
}
}

}
return 1;
}
int
CreateSMatrix(TSMatrix &M)
//创建新的稀疏矩阵
{
//以下是对寻找每行的第一个非零元在data动态数组中的位置
int num[MAXRC];
int t;
for(t=1;t<=M.mu;t++)num[t]=0;
for(t=1;t<=M.tu;++t)++num[M.data[t].i];
M.rpos[1]=1;
//求第ran行第一个非零元在Q.data中的位置
int ran=1;
for( ran=2;ran<=M.mu;++ran){ M.rpos[ran]=M.rpos[ran-1]+num[ran-1];

}
return 1;
}
int

1.它这个程序中,数组的下标为0的元素都是不用的,所有声明时长度要+1
2.ctemp是用来作乘法时,累积求和用的.既然是求和用的,初始化肯定是0.假设是2x3矩阵和3x4矩阵相乘.前者的每行要和后者的4列分别相乘,所以ctemp的长度要设为4+1=5.
3.这个乘法函数是逐行计算的,每算完1行,Q.tu就记录了目前为止已经得到的非零元的个数,所以新行的rpos肯定是Q.tu+1.这点从最后的
if(ctemp[ccol])
{
if(++Q.tu>MAXSIZE)
return 0;
就可以看的出来,每得到一个非零元,就要执行一次++Q.tu

4.这个Create函数有点问题,如果第一行没有非零元的话,我个人认为应该将M.rpos[1]设为0.当然,为了不影响其他行的计算,可以在其他行算完后,再由
if(num[1]==0) M.rpos[1]=0;来设置
温馨提示:答案为网友推荐,仅供参考
第1个回答  2009-04-22
你的完整的程序呢?这个程序代码很乱,风格也不好:-)

int ctemp[N.nu+1];////////这里能这样定义吗????????????
这样是不对的,要采用动态分配
int *ctemp=new int[N.nu+1];使用完后要用delete []ctemp;释放内存

for(arow=1;arow<=M.mu;++arow)
{ int i;
for(i=1;i<=N.nu;i++)ctemp[i]=0;//////////这啥意思呢???????????
这里的话表面上看来就是数组初始化,这是很常见的情况,在数组使用前要将其初始化为0,不然可能是一个很大的负数
Q.rpos[arow]=Q.tu+1;///////////还有这里???????
这里应该就是乘法的运算部分了,你应该先仔细了解一下乘法的运算过程,可以自己独立的尝试着写一个,然后再对照别人的程序就应该比较容易理解了^_^
希望我的回答对你有帮助。本回答被提问者采纳
第2个回答  2019-02-20
你的完整的程序呢?这个程序代码很乱,风格也不好:-)
int
ctemp[N.nu+1];////////这里能这样定义吗????????????
这样是不对的,要采用动态分配
int
*ctemp=new
int[N.nu+1];使用完后要用delete
[]ctemp;释放内存
for(arow=1;arow<=M.mu;++arow)
{
int
i;
for(i=1;i<=N.nu;i++)ctemp[i]=0;//////////这啥意思呢???????????
这里的话表面上看来就是数组初始化,这是很常见的情况,在数组使用前要将其初始化为0,不然可能是一个很大的负数
Q.rpos[arow]=Q.tu+1;///////////还有这里???????
这里应该就是乘法的运算部分了,你应该先仔细了解一下乘法的运算过程,可以自己独立的尝试着写一个,然后再对照别人的程序就应该比较容易理解了^_^
希望我的回答对你有帮助。