資料結構——稀疏矩陣運算器(C語言)
阿新 • • 發佈:2018-11-07
資料結構——稀疏矩陣運算器(C語言)
/*****************稀疏矩陣運算器 ****************/ #include<stdio.h> #include<stdlib.h> #define OK 1 #define TRUE 1 #define ERROR 0 #define FALSE 0 #define MAX_SIZE 100 typedef struct{ //構造三元組 int x; int y; int e; }Triad; typedef struct { int mrow,mcol,ms; Triad data[MAX_SIZE]; }Rtriad; void Input(Rtriad &S){ //以三元組方式輸入矩陣 printf("請輸入行,列(row col):"); scanf("%d%d",&S.mrow,&S.mcol); printf("請以行序為主序,以三元組的方式輸入矩陣元素,'-1 -1 -1'表示結束:\n"); int x,y,z; scanf("%d%d%d",&x,&y,&z); S.ms=0; while(!(x==-1&&y==-1&&z==-1)){ //長度為S.ms+1,從0開始到S.ms S.data[S.ms].x=x; S.data[S.ms].y=y; S.data[S.ms].e=z; S.ms++; scanf("%d%d%d",&x,&y,&z); } S.ms--; } void Add(Rtriad S1,Rtriad S2,Rtriad &S3){ //矩陣相加 if(S1.mcol!=S2.mcol||S1.mrow!=S2.mrow){ printf("ERROR!!!\n"); return ; } S3.mcol=S1.mcol ; S3.mrow=S1.mrow ; S3.ms=0; int row,col,s,x,y,z; for(row=1;row<=S3.mrow;row++){ for(col=1;col<=S3.mcol;col++){ z=0; for(s=0;s<=S1.ms;s++){ if(S1.data[s].x==row&&S1.data[s].y==col){ S3.data[S3.ms].x=row; S3.data[S3.ms].y=col; S3.data[S3.ms].e=S1.data[s].e; z++; } } for(s=0;s<=S2.ms;s++){ if(S2.data[s].x==row&&S2.data[s].y==col){ S3.data[S3.ms].x=row; S3.data[S3.ms].y=col; if(z==0) S3.data[S3.ms].e=S2.data[s].e; else S3.data[S3.ms].e+=S2.data[s].e; z++; } } if(z!=0) S3.ms++; } } int m=0; for(int t=0;t<=S3.ms;t++){ if(S3.data[t].e==0){ //刪除 for(int i=t+1;i<S3.ms;i++){ S3.data[i-1]=S3.data[i]; } m++; } } S3.ms-=m; } void Printf(Rtriad S){ //列印矩陣 int a[S.mrow][S.mcol]; for(int i=0;i<S.mrow;i++) for(int j=0;j<S.mcol;j++) a[i][j]=0; for(int k=0;k<=S.ms;k++) a[S.data[k].x-1][S.data[k].y-1]=S.data[k].e; //printf("\n\n矩陣為:\n"); for(int i=0;i<S.mrow;i++){ for(int j=0;j<S.mcol;j++) printf("%-2d ",a[i][j]); printf("\n"); } } void Sub(Rtriad S1,Rtriad S2,Rtriad &S3){ //矩陣相減 for(int i=0;i<=S2.ms;i++) S2.data[i].e*=-1; Add(S1,S2,S3); for(int i=0;i<=S2.ms;i++) S2.data[i].e*=-1; } void Mult(Rtriad S1,Rtriad S2,Rtriad &S3){ //矩陣相乘 if(S1.mcol!=S2.mrow){ printf("ERROR!!!\n"); return ; } S3.mrow=S1.mrow; S3.mcol=S2.mcol; S3.ms=0; int s1[S1.mrow][S1.mcol]; int s2[S2.mrow][S2.mcol]; int s3[S3.mrow][S3.mcol]; for(int i=0;i<S1.mrow;i++) for(int j=0;j<S1.mcol;j++) s1[i][j]=0; for(int i=0;i<S2.mrow;i++) for(int j=0;j<S2.mcol;j++) s2[i][j]=0; for(int i=0;i<S3.mrow;i++) for(int j=0;j<S3.mcol;j++) s3[i][j]=0; for(int k=0;k<=S1.ms;k++) s1[S1.data[k].x-1][S1.data[k].y-1]=S1.data[k].e; for(int k=0;k<=S2.ms;k++) s2[S2.data[k].x-1][S2.data[k].y-1]=S2.data[k].e; for(int row=0;row<S3.mrow;row++){ for(int col=0;col<S3.mcol;col++){ for(int k=0;k<S1.mcol;k++) s3[row][col]+=(s1[row][k]*s2[k][col]); if(s3[row][col]!=0){ S3.data[S3.ms].x=row+1; S3.data[S3.ms].y=col+1; S3.data[S3.ms].e=s3[row][col]; S3.ms++; } } } } void Tran(Rtriad &S1,Rtriad &S2){ //矩陣的快速轉置 S2.ms=S1.ms; S2.mcol=S1.mrow; S2.mrow=S1.mcol; int num[MAX_SIZE]; //每一列的元素個數 ,從1開始計數 int pos[MAX_SIZE]; for(int col=1;col<=S1.mcol;col++) //初始化num num[col]=0; for(int i=0;i<=S1.ms;i++) //給num賦值 ,num從1開始 num[S1.data[i].y]++; pos[1]=1; //給pos賦值 ,pos從1開始 for(int col=2;col<=S1.mcol;col++) pos[col]=pos[col-1]+num[col-1]; for(int k=0;k<=S1.ms;k++){ //S1,S2都是從data[0]開始的 int col=S1.data[k].y; int q=pos[col]; S2.data[q-1].e=S1.data[k].e; S2.data[q-1].x=S1.data[k].y; S2.data[q-1].y=S1.data[k].x; pos[col]++; } } int main(){ printf("/*****************稀疏矩陣運算器 ****************/\n\n"); printf("功能選擇:\n1.矩陣相加\n2.矩陣相減\n3.矩陣相乘\n4.矩陣轉置\n"); int n; printf("選擇功能:"); scanf("%d",&n); Rtriad S1,S2,S3; switch(n){ case 1: printf("\n請輸入矩陣1:\n"); Input(S1); printf("\n請輸入矩陣2:\n"); Input(S2); Add(S1,S2,S3); printf("\n結果為:\n"); Printf(S3); break; case 2: printf("\n請輸入矩陣1:\n"); Input(S1); printf("\n請輸入矩陣2:\n"); Input(S2); Sub(S1,S2,S3); printf("\n結果為:\n"); Printf(S3); break; case 3: printf("\n請輸入矩陣1:\n"); Input(S1); printf("\n請輸入矩陣2:\n"); Input(S2); Mult(S1,S2,S3); printf("\n結果為:\n"); Printf(S3); break; case 4: printf("\n請輸入矩陣1:\n"); Input(S1); Tran(S1,S2); printf("\n結果為:\n"); Printf(S3); break; } return 0; }