文档库 最新最全的文档下载
当前位置:文档库 › 矩阵算法

矩阵算法

c语言矩阵的运算的算法 

#include
#include
using namespace std;
const int MAXSIZE=100; // 定义非零元素的对多个数
const int MAXROW=10; // 定义数组的行数的最大值
typedef struct // 定义三元组的元素
{
int i,j;
int e;
}Triple;
typedef struct // 定义普通三元组对象
{
Triple data[MAXSIZE+1];
int mu,nu,tu;
}TSMatrix;
typedef struct// 定义带链接信息的三元组对象
{
Triple data[MAXSIZE+2];
int rpos[MAXROW+1];
int mu,nu,tu;
}RLSMatrix;

template
bool InPutTSMatrix(P & T,int y)//输入矩阵,按三元组格式输入
{
cout<<"输入矩阵的行,列和非零元素个数:"<cin>>T.mu>>T.nu>>T.tu;
cout<<"请输出非零元素的位置和值:"<int k=1;
for(;k<=T.tu;k++)
cin>>T.data[k].i>>T.data[k].j>>T.data[k].e;
return true;
}

template
int OutPutSMatrix(P T)// 输出矩阵,按标准格式输出
{
int m,n,k=1;
for(m=0;m{
for(n=0;n{
if((T.data[k].i-1)==m&&(T.data[k].j-1)==n)
{
cout.width(4);
cout<}
else
{
cout.width(4);
cout<<"0";
}
}
cout<}
return 1;
}
// 求矩阵的转置矩阵
int TransposeSMatrix( )
{
TSMatrix M,T; //定义预转置的矩阵
InPutTSMatrix(M, 0); //输入矩阵
int num[MAXROW+1];
int cpot[MAXROW+1]; // 构建辅助数组
int q,p,t;
T.tu=M.tu; T.mu=M.nu; T.nu=M.mu;
if(T.tu)
{
for(int col=1;col<=M.nu;col++) num[col]=0;
for(t=1;t<=M.tu;t++) ++num[M.data[t].j];
cpot[1]=1;
for(int i=2;i<=M.nu;i++) cpot[i]=cpot[i-1]+num[i-1];//求出每一列中非零元素在三元组中出现的位置
for(p=1;p<=M.tu;p++)
{
col=M.data[p].j; q=cpot[col];
T.data[q].i=col; T.data[q].j=M.data[p].i;
T.data[q].e=M.data[p].e; ++cpot[col];
}
}
cout<<"输入矩阵的转置矩阵为"<OutPutSMatrix(T);
return 1;
}

bool Count(RLSMatrix &T)
{
int num[MAXROW+1];
for(int col=1;col<=T.mu;col++) num[col]=0;
for(col=1;col<=T.tu;col++) ++num[T.data[col].i];
T.rpos[1]=1;
for(int i=2;i<=T.mu;i++) T.rpos[i]=T.rpos[i-1]+num[i-1]; // 求取每一行中非零元素在三元组中出现的位置

return true;
}
// 两个矩阵相乘
bool MultSMatrix ( )
{
RLSMatrix M,N,Q; // 构建三个带“链接信息”的三元组表示的数组
InPutTSMatrix(M,1); // 用普通三元组形式输入数组
InPutTSMatrix(N,1);
Count(M); Count(N);
if(M.nu!=N.mu) return false;
Q.mu=M.mu; Q.nu=N.nu; Q.tu=0; // Q初始化
int ctem

p[MAXROW+1]; // 辅助数组
int arow,tp,p,brow,t,q,ccol;
if(M.tu*N.tu)
{ // Q是非零矩阵
for( arow=1;arow<=M.mu;arow++)
{
///memset(ctemp,0,N.nu);
for(int x=1;x<=N.nu;x++) // 当前行各元素累加器清零
ctemp[x]=0;
Q.rpos[arow]=Q.tu+1; // 当前行的首个非零元素在三元组中的位置为此行前所有非零元素+1
if(arowelse tp=M.tu+1;
for(p=M.rpos[arow];p{ // 对当前行每个非零元素进行操作

brow=M.data[p].j; // 在N中找到i值也操作元素的j值相等的行
if(browelse t=N.tu+1;
for(q=N.rpos[brow];q{ // 对找出的行当每个非零元素进行操作

ccol=N.data[q].j;
ctemp[ccol] += M.data[p].e*N.data[q].e; // 将乘得到对应值放在相应的元素累加器里面
}
}
for(ccol=1;ccol<=Q.nu;ccol++) // 对已经求出的累加器中的值压缩到Q中
if(ctemp[ccol])
{
if(++Q.tu>MAXSIZE) return false;
Q.data[Q.tu].e=ctemp[ccol];
Q.data[Q.tu].i=arow;
Q.data[Q.tu].j=ccol;
}
}
}
OutPutSMatrix(Q);
return true;
}
typedef struct OLNode// 定义十字链表元素
{
int i,j;
int e;
struct OLNode *right,*down; // 该非零元所在行表和列表的后继元素
}OLNode,*OLink;
typedef struct//定义十字链表对象结构体
{
OLink *rhead,*chead;
int mu,nu,tu; //系数矩阵的行数,列数,和非零元素个数
}CrossList;
bool CreateSMatrix_OL(CrossList & M)//创建十字链表
{
int x,y,m;

cout<<"请输入矩阵的行,列,及非零元素个数"<cin>>M.mu>>M.nu>>M.tu;
if(!(M.rhead=(OLink*)malloc((M.mu+1)*sizeof(OLink)))) exit(0);
if(!(M.chead=(OLink*)malloc((M.nu+1)*sizeof(OLink)))) exit(0);
for(x=0;x<=M.mu;x++)
M.rhead[x]=NULL; // 初始化各行,列头指针,分别为NULL
for(x=0;x<=M.nu;x++)
M.chead[x]=NULL;
cout<<"请按三元组的格式输入数组:"<for(int i=1;i<=M.tu;i++)
{
cin>>x>>y>>m; //按任意顺序输入非零元,(普通三元组形式输入)
OLink p,q;
if(!(p=(OLink)malloc(sizeof(OLNode))))
exit(0); // 开辟新节点,用来存储输入的新元素
p->i=x; p->j=y; p->e=m;
if(M.rhead[x]==NULL||M.rhead[x]->j>y)
{
p->right=M.rhead[x]; M.rhead[x]=p;
}
else
{


for(q=M.rhead[x];(q->right)&&(q->right->jright); //查找节点在行表中的插入位置
p->right=q->right; q->right=p; // 完成行插入
}
if(M.chead[y]==NULL||M.chead[y]->i>x)
{
p->down=M.chead[y]; M.chead[y]=p;
}
else{
for(q=M.chead[y];(q->down)&&(q->down->idown);//查找节点在列表中的插入位置
p->down=q->down;
q->down=p; // 完成列插入

}
}
return true;
}
bool OutPutSMatrix_OL(CrossList T)// 输出十字链表,用普通数组形式输出
{
for(int i=1;i<=T.mu;i++)
{
OLink p=T.rhead[i];
for(int j=1;j<=T.nu;j++)
{
if((p)&&(j==p->j))
{
cout<e;
p=p->right;
}
else
cout<}
cout<}
return true;
}

//矩阵的加法
bool AddSMatrix()
{
CrossList M,N; // 创建两个十字链表对象,并初始化
CreateSMatrix_OL(M);
CreateSMatrix_OL(N);
cout<<"输入的两矩阵的和矩阵为:"<OLink pa,pb,pre ,hl[MAXROW+1]; //定义辅助指针,pa,pb分别为M,N当前比较的元素,pre为pa的前驱元素
for(int x=1;x<=M.nu;x++) hl[x]=M.chead[x];
for(int k=1;k<=M.mu;k++)// 对M的每一行进行操作
{
pa=M.rhead[k]; pb=N.rhead[k]; pre=NULL;
while(pb)
{ // 把N中此行的每个元素取出,
OLink p;
if(!(p=(OLink)malloc(sizeof(OLNode)))) exit(0); // 开辟新节点,存储N中取出的元素
p->e=pb->e; p->i=pb->i; p->j=pb->j;
if(NULL==pa||pa->j>pb->j)// 当M此行已经检查完或者pb因该放在pa前面
{

if(NULL==pre)
M.rhead[p->i]=p;
else
pre->right=p;
p->right=pa; pre=p;
if(NULL==M.chead[p->j])// 进行列插入
{
M.chead[p->j]=p; p->down=NULL;
}
else
{
p->down=hl[p->j]->down; hl[p->j]->down=p;
}
hl[p->j]=p;
pb=pb->right;
}
else
if((NULL!=pa)&&pa->jj)// 如果此时的pb元素因该放在pa后面,则取以后的pa再来比较
{
pre=pa;
pa=pa->right;
}
else
if(pa->j==pb->j)// 如果pa,pb位于同一个位置上,则将值相加
{
pa->e += pb->e;
if(!pa->e)
{ // 如果相加后的和为0,则删除此节点,

同时改变此元素坐在行,列的前驱元素的相应值
if(NULL==pre) // 修改行前驱元素值
M.rhead[pa->i]=pa->right;
else
pre->right=pa->right;
p=pa;
pa=pa->right;
if(M.chead[p->j]==p)
M.chead[p->j]=hl[p->j]=p->down; // 修改列前驱元素值
else
hl[p->j]->down=p->down;
free(p); pb=pb->right;
}
else
{
pa=pa->right; pb=pb->right;
}
}

}
}
OutPutSMatrix_OL(M);
return true;
}
int main()
{
cout.fill('*');
cout<cout.fill(' ');
// system("color 0C");
cout<cout.fill('*');
cout<cout.fill(' ');
cout<<"请选择要进行的操作:"<cout<<"1:矩阵的转置。"<cout<<"2:矩阵的加(减)法。"<cout<<"3:矩阵的乘法。"<cout<<"4:推出程序。"<char c;
do
{
cin.clear();
cout<<"请输入你要的操作:"<c=getchar();
if(c=='1')
TransposeSMatrix( ); //调用矩阵转置函数
else
if(c=='2')
AddSMatrix(); //调用矩阵相加函数
else
if(c=='3')
MultSMatrix (); //调用矩阵相乘函数
else
exit(0); //退出
return 0;

}while(c!=4);
}


相关文档