稀疏矩陣的轉置c語言
㈠ c語言矩陣轉置問題
其實只是小問題,你自己都編的很好了。就是保存屏幕不在按入Q和Enter鍵屏幕不會馬上消失上面有問題:
你可以用兩個getchar()函數來讀取鍵盤輸入,前一個數緩沖enter鍵,後一個等待鍵盤輸入,然後屏幕消失!
代碼已修改,如下:
#include <stdio.h>
#include <stdlib.h>
#define MAXSIZE 20 /*矩陣中最大非零元的個數*/
typedef struct triple
{
int i; /*行標,本程序中從1開始的*/
int j; /*列標,本程序中從1開始的*/
int e; /*非零元*/
}Triple; /*三元組定義*/
typedef struct tabletype
{
int mu; /*矩陣的行數*/
int nu; /*列數*/
int tu; /*非零元個數*/
Triple data[MAXSIZE+1]; /*非零元的三元組表,*/
}Tabletype; /*三元組線性表*/
void out_matrix(Tabletype *); /*輸出 矩陣*/
/*以下為轉置程序,將a所指矩陣轉置,將結果存入b所指的矩陣中*/
int TransposeSMatrix(Tabletype *,Tabletype *);
int main( void )
{
char ch;
while(1)
{
printf(" @@@@@@@@@@本程序的功能是實現稀疏矩陣的普通轉置@@@@@@@@@@@@@@@@@@@\n");
printf(" @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@\n");
/*源矩陣a*/
Tabletype a= {6,7,8,{ {1,2,12},{1,3,9},{3,1,-3},{3,6,14},{4,3,24},{5,2,18},{6,1,15},{6,4,-7} }};
Tabletype b; /*聲明矩陣b*/
printf("The source Matrix:\n");
out_matrix(&a);
if(TransposeSMatrix(&a,&b)) /*若a不為零矩陣則轉置a,存入b中*/
{ printf("After TransposeSMatrix: \n");
out_matrix(&b);
}
else
{
printf("The matrix is zeros:\n");
out_matrix(&a);
}
do{
printf("Input 'q' to quit and ENTER run again:");
if((ch = getchar()) == 'q' || ch == 'Q')
getchar(); //讀取enter
getchar();//任意字元
exit(0);
}while(ch!='\n');
system("cls");
}
return 1;
}
void out_matrix(Tabletype *a) /* 列印矩陣*/
{
int i,j,k = 0;
for(i = 1 ;i <= a->mu; i++)
{
for(j = 1; j<= a->nu; j++)
{ /*判斷是否為非零元*/
if((a->data[k].i == i)&&(a->data[k].j == j))
{
printf("%4d",a->data[k].e);
k++;
}
else
printf("%4d",0);
}
printf("\n");
}
}
int TransposeSMatrix(Tabletype *a,Tabletype *b)
{
int p,q,col;
b->mu = a->nu; /*原矩陣的行數為新矩陣的列數,願列數為新行數,非零元個數不變*/
b->nu = a->mu;
b->tu = a->tu;
if(b->tu) /*若a不為零矩陣*/
{
q = 0; /*b->data下標*/
for(col = 1; col < a->nu; col++)
for(p = 0;p < a->tu;p++) /*p為a->data的下標*/
if(col == a->data[p].j) /*按b->data[q]中的列標對a->data[p]進行掃描*/
{
b->data[q].i = a->data[p].j;
b->data[q].j = a->data[p].i;
b->data[q].e = a->data[p].e;
q++;
}
return 1;
}
else /*a為零矩陣*/
return 0;
}
不知道是不是你的要求。希望能幫助你!
㈡ c++ 十字鏈表實現稀疏矩陣的轉置
mplate <class Type>SparseMatrix<Type>
SparseMatrix<Type>::SparseMatrix::FastTranspose()
{
int *RowSize = new int[Cols]; // 統計各列非零元素個數
int *RowStart = new int[Cols]; // 預計轉置後各行存放位置
SparseMatrix b; // 存放轉置結果
b.Rows = cols; b.cols = Rows; b.Terms = Terms;
if (Terms>0) //nonzero matrix
{
for (int i=0;i<Cols;i++) RowSize[i] = 0; //initialize
for (i=0;i<terms;i++) RowSize[smArray[i].col]++;
//RowStart[i]=starting position of row i in b
RowStart[0]=0;
for (i=1;i<Cols;i++) RowStart[i] = RowStart[i-1]+
RowSize[i-1];
for (i=0;i<Terms;i++) //move from a to b
{
int j=Rowstart[smArray[i].col];
b.smArray[j].row=smArray[i].col;
b.smArray[j].col= smArray[i].row;
b.smArray[j].value= smArray[i].value;
RowStart[smArray[i].col]++;
} //end of for
}
delete [ ]Rowsize;
delete [ ]Rowstart;
return b;
}
另外,站長團上有產品團購,便宜有保證
㈢ 求一個C++的稀疏矩陣類,要求能實現加法,減法和乘法,正常輸出。還能轉置。。。急!!!急!!!
#include <iostream.>
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 a,b,c; //行數,列數,非零元個數
}TSMatrix;
typedef struct { // 定義帶鏈接信息的三元組對象
Triple data[MAXSIZE+2];
int rpos[MAXROW+1];
int a,b,c;
}RLSMatrix;
template <class P>
int shuru(P & T,int y){ //輸入矩陣,按三元組格式輸入
cout<<"輸入稀疏矩陣的行,列和非零元素個數:"<<endl;
cin>>T.a>>T.b>>T.c;
cout<<"請輸出非零元素的位置和值:"<<endl;
int k=1;
for(;k<=T.c;k++)
cin>>T.data[k].i>>T.data[k].j>>T.data[k].e;
return 1;
}
template <class P>
void shuchu(P T){ // 輸出矩陣,按標准格式輸出
int m,n,k=1;
for(m=0;m<T.a;m++){
for(n=0;n<T.b;n++){
if((T.data[k].i-1)==m&&(T.data[k].j-1)==n){
cout.width(4);
cout<<T.data[k++].e;}
else{
cout.width(4); cout<<"0"; }
}
cout<<endl;
}
}
void zhuan( ) // 求矩陣的轉置矩陣
{
TSMatrix M,T; //定義預轉置的矩陣
shuru(M, 0); //輸入矩陣
int num[MAXROW+1];
int cpot[MAXROW+1]; // 構建輔助數組
int q,p,t;
T.c=M.c; T.a=M.b; T.b=M.a;
if(T.c){
for(int col=1;col<=M.c;col++) num[col]=0;
for(t=1;t<=M.c;t++) ++num[M.data[t].j];
cpot[1]=1;
for(int i=2;i<=M.b;i++) cpot[i]=cpot[i-1]+num[i-1]; // 求出每一列中非零元素在三元組中出現的位置
for(p=1;p<=M.c;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<<"輸入稀疏矩陣的轉置矩陣為"<<endl;
shuchu(T);
}
void Count(RLSMatrix &T) // 求取每一行中非零元素在三元組中出現的位置
{
int num[MAXROW+1];
for(int col=1;col<=T.a;col++) num[col]=0;
for(col=1;col<=T.c;col++) ++num[T.data[col].i];
T.rpos[1]=1;
for(int i=2;i<=T.a;i++) T.rpos[i]=T.rpos[i-1]+num[i-1]; }
typedef struct OLNode // 定義十字鏈表元素
{
int i,j; //該非零元的行列下標
int e; //非零元值
struct OLNode *right,*down; // 該非零元所在行表和列表的後繼元素
}OLNode,*OLink; typedef struct // 定義十字鏈表對象結構體
{
OLink *rhead,*chead; //
int a,b,c; // 系數矩陣的行數,列數,和非零元素個數
}CrossList; void CreateSMatrix_OL(CrossList & M) // 創建十字鏈表
{
int x,y,m;
cout<<"請輸入稀疏矩陣的行,列,及非零元素個數"<<endl;
cin>>M.a>>M.b>>M.c;
if(!(M.rhead=(OLink*)malloc((M.a+1)*sizeof(OLink)))) exit(0);
if(!(M.chead=(OLink*)malloc((M.b+1)*sizeof(OLink)))) exit(0);
for(x=0;x<=M.a;x++)
M.rhead[x]=NULL; // 初始化各行,列頭指針,分別為NULL
for(x=0;x<=M.b;x++)
M.chead[x]=NULL;
cout<<"請按三元組的格式輸入數組:"<<endl;
for(int i=1;i<=M.c;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->j<y);q=q->right); // 查找節點在行表中的插入位置
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->i<x);q=q->down); // 查找節點在列表中的插入位置
p->down=q->down; q->down=p; // 完成列插入 }
}
} void shuchu(CrossList T){ // 輸出十字鏈表,用普通數組形式輸出
for(int i=1;i<=T.a;i++){
OLink p=T.rhead[i];
for(int j=1;j<=T.b;j++){
if((p)&&(j==p->j)){
cout<<p->e; p=p->right;
}
else
cout<<"0";
}
cout<<endl;
}
}
void chengfa() //矩陣的乘法
{
CrossList M,N; // 創建兩個十字鏈表對象,並初始化
CreateSMatrix_OL(M);
CreateSMatrix_OL(N);
cout<<"輸入的兩稀疏矩陣的積為:"<<endl;
OLink pa,pb,pre ,hl[MAXROW+1]; //定義輔助指針,pa,pb分別為M,N當前比較的元素,pre為pa的前驅元素
for(int x=1;x<=M.b;x++) hl[x]=M.chead[x];
for(int k=1;k<=M.a;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->j<pb->j){ // 如果此時的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;
}
}
}
}
shuchu(M);
}
void jianfa() //矩陣的減法
{
CrossList M,N; // 創建兩個十字鏈表對象,並初始化
CreateSMatrix_OL(M);
CreateSMatrix_OL(N);
cout<<"輸入的兩稀疏矩陣的差矩陣為:"<<endl;
OLink pa,pb,pre ,hl[MAXROW+1]; //定義輔助指針,pa,pb分別為M,N當前比較的元素,pre為pa的前驅元素
for(int x=1;x<=M.b;x++) hl[x]=M.chead[x];
for(int k=1;k<=M.a;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->j<pb->j){ // 如果此時的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;
}
}
}
}
shuchu(M);
} void add() //矩陣的加法
{
CrossList M,N; // 創建兩個十字鏈表對象,並初始化
CreateSMatrix_OL(M);
CreateSMatrix_OL(N);
cout<<"輸入的兩稀疏矩陣的和矩陣為:"<<endl;
OLink pa,pb,pre ,hl[MAXROW+1]; //定義輔助指針,pa,pb分別為M,N當前比較的元素,pre為pa的前驅元素
for(int x=1;x<=M.b;x++) hl[x]=M.chead[x];
for(int k=1;k<=M.a;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->j<pb->j){ // 如果此時的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;
}
}
}
}
shuchu(M);
} int main() //主函數
{
cout<<"1:稀疏矩陣的加法。"<<endl;
cout<<"2:稀疏矩陣的乘法。"<<endl;
cout<<"3:稀疏矩陣的減法。"<<endl;
cout<<"4:稀疏矩陣的轉置."<<endl;
cout<<"0:退出程序。"<<endl;
char c=getchar();
if(c=='1')
add(); //調用矩陣相加函數
else
if(c=='2')
chengfa(); //調用矩陣相乘函數
else
if(c=='3')
jianfa(); //調用矩陣相減函數
else
if(c=='4')
zhuan( ); //調用矩陣轉置函數
else
exit(0); //退出
return 0;
}
㈣ C 語言稀疏矩陣的快速轉置問題
你的這個問題很多啊,我先給你看看,到時候再給你。。我覺得你最好把你各個步驟寫個注釋,寫個大概的注釋,不然我都不知道你在干什麼。。。
說說題目的要求,你的那個好像是只處理n行三列的是嗎??我都被那個搞暈了。。寫出題目要求。。。問題真的很多。。。
㈤ c++ 編程稀疏矩陣的轉置
三元組格式是這個樣子吧{r,c,d} //r 為行,c為列,d為數據
轉置只要把r和c交換一下,然後排序輸出即可。
㈥ 用十字鏈表存儲結稀疏矩陣,並進行矩陣的轉置。 要C的,c++的我看不懂。。。。~
這個吧 功能比你要的還多:http://wenku..com/view/3d744dd950e2524de5187e68.html
建立稀疏矩陣A 的十字鏈表首先輸入的信息是:m(A 的行數),n(A 的列數),r(非零項的數目),緊跟著輸入的是r 個形如(i,j,aij)的三元組。
演算法的設計思想是:首先建立每行(每列)只有頭結點的空鏈表,並建立起這些頭結點拉成的循環鏈表;然後每輸入一個三元組(i,j,aij),則將其結點按其列號的大小插入到第i 個行鏈表中去,同時也按其行號的大小將該結點插入到第j 個列鏈表中去。在演算法中將利用一個輔助數組MNode *hd[s+1]; 其中s=max(m , n) , hd [i]指向第i 行(第i 列)鏈表的頭結點。這樣做可以在建立鏈表時隨機的訪問任何一行(列),為建表帶來方便。
演算法如下:
MLink CreatMLink( ) /* 返回十字鏈表的頭指針*/
{
MLink H;
Mnode *p,*q,*hd[s+1];
int i,j,m,n,t;
datatype v;
scanf(「%d,%,%d」,&m,&n,&t);
H=malloc(sizeof(MNode)); /*申請總頭結點*/
H->row=m; H->col=n;
hd[0]=H;
for(i=1; i<S; i++)
{ p=malloc(sizeof(MNode)); /*申請第i 個頭結點*/
p->row=0; p->col=0;
p->right=p; p->down=p;
hd[i]=p;
hd[i-1]->v_next.next=p;
}
hd[S]->v_next.next=H; /*將頭結點們形成循環鏈表*/
for (k=1;k<=t;k++)
{ scanf (「%d,%d,%d」,&i,&j,&v); /*輸入一個三元組,設值為int*/
p=malloc(sizeof(MNode));
p->row=i ; p->col=j; p->v_next.v=v
/*以下是將*p 插入到第i 行鏈表中去,且按列號有序*/
q=hd[i];
while ( q->right!=hd[i] && (q->right->col)<j ) /*按列號找位置*/
q=q->right;
p->right=q->right; /*插入*/
q->right=p;
/*以下是將*p 插入到第j 行鏈表中去,且按行號有序*/
q=hd[i];
while ( q->down!=hd[j] && (q->down->row)<i ) /*按行號找位置*/
q=q->down;
p-> down =q-> down; /*插入*/
q-> down =p;
} /*for k*/
return H;
} /* CreatMLink */
㈦ 關於稀疏矩陣的數組存儲表示,轉置,輸出
#include<iostream>
using std::cout;
using std::cin;
using std::endl;
struct node
{
int r;//行標
int c;//列標
double dat;//數據
};
class triple
{
private:
int row;//行數
int col;//列數
int num;//非零個數
node *ptr;//存放數組的首地址
public:
triple(int co,int ro,int nu):col(co),row(ro),num(nu)
{
ptr=new node[num];//分配num,盛放num個元素
cout<<"請輸入"<<num<<"個三元組元素\n"<<"格式為: 2 3 6.7\n其中2為行標,3為列標,6.7為數據元素"<<endl;
for(int i=0;i<num;i++)
{
cin>>ptr[i].r;
cin>>ptr[i].c;
cin>>ptr[i].dat;
}
}
~triple(){delete[]ptr;}
void print()
{
int flag=ptr[0].r;
cout<<"第"<<flag<<"行元素為:";
for(int i=0;i<num;i++)
{
if(ptr[i].r!=flag)
{
cout<<"\n";
flag=ptr[i].r;
cout<<endl;
cout<<"第"<<flag<<"行元素為:";
}
cout<<"("<<ptr[i].r<<","<<ptr[i].c<<","<<ptr[i].dat<<") ";
}
}
void transpose()
{
int flag=0;
for(int i=1;i<=col;i++)
{
for(int j=0;j<num;j++)
{
if(ptr[j].c==i)
{
if(flag!=ptr[j].c)
{
flag=ptr[j].c;
cout<<"\n第"<<ptr[j].c<<"行為:";
}
cout<<"("<<ptr[j].c<<","<<ptr[j].r<<","<<ptr[j].dat<<") ";
}
}
}
}
};
void main()
{
cout<<"請輸入數組的行列和元素個數:\n";
int a[3];
for(int i=0;i<3;i++)
{
cin>>a[i];
}
triple t(a[0],a[1],a[2]);
t.print();//輸出原矩陣
cout<<"轉制後的矩陣為:";
t.transpose();
}
㈧ 稀疏矩陣的轉置運算用C語言
#include<string.h>
#include<ctype.h>
#include<malloc.h> // malloc()等
#include<limits.h> // INT_MAX等
#include<stdio.h> // EOF(=^Z或F6),NULL
#include<stdlib.h> // atoi()
#include<io.h> // eof()
#include<math.h> // floor(),ceil(),abs()
#include<process.h> // exit()
#include<iostream.h> // cout,cin
// 函數結果狀態代碼
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
// #define OVERFLOW -2 因為在math.h中已定義OVERFLOW的值為3,故去掉此行
typedef int Status; // Status是函數的類型,其值是函數結果狀態代碼,如OK等
typedef int Boolean; // Boolean是布爾類型,其值是TRUE或FALSE
typedef int ElemType;
// c5-2.h 稀疏矩陣的三元組順序表存儲表示
#define MAXSIZE 100 // 非零元個數的最大值
struct Triple
{
int i,j; // 行下標,列下標
ElemType e; // 非零元素值
};
struct TSMatrix
{
Triple data[MAXSIZE+1]; // 非零元三元組表,data[0]未用
int mu,nu,tu; // 矩陣的行數、列數和非零元個數
};
// bo5-2.cpp 三元組稀疏矩陣的基本操作,包括演算法5.1(9個)
Status CreateSMatrix(TSMatrix &M)
{ // 創建稀疏矩陣M
int i,m,n;
ElemType e;
Status k;
printf("請輸入矩陣的行數,列數,非零元素數:");
scanf("%d,%d,%d",&M.mu,&M.nu,&M.tu);
M.data[0].i=0; // 為以下比較順序做准備
for(i=1;i<=M.tu;i++)
{
do
{
printf("請按行序順序輸入第%d個非零元素所在的行(1~%d),列(1~%d),元素值:",i,M.mu,M.nu);
scanf("%d,%d,%d",&m,&n,&e);
k=0;
if(m<1||m>M.mu||n<1||n>M.nu) // 行或列超出范圍
k=1;
if(m<M.data[i-1].i||m==M.data[i-1].i&&n<=M.data[i-1].j) // 行或列的順序有錯
k=1;
}while(k);
M.data[i].i=m;
M.data[i].j=n;
M.data[i].e=e;
}
return OK;
}
void DestroySMatrix(TSMatrix &M)
{ // 銷毀稀疏矩陣M
M.mu=0;
M.nu=0;
M.tu=0;
}
void PrintSMatrix(TSMatrix M)
{ // 輸出稀疏矩陣M
int i;
printf("%d行%d列%d個非零元素。\n",M.mu,M.nu,M.tu);
printf("行 列 元素值\n");
for(i=1;i<=M.tu;i++)
printf("%2d%4d%8d\n",M.data[i].i,M.data[i].j,M.data[i].e);
}
Status CopySMatrix(TSMatrix M,TSMatrix &T)
{ // 由稀疏矩陣M復製得到T
T=M;
return OK;
}
int comp(int c1,int c2) // 另加
{ // AddSMatrix函數要用到
int i;
if(c1<c2)
i=1;
else if(c1==c2)
i=0;
else
i=-1;
return i;
}
Status AddSMatrix(TSMatrix M,TSMatrix N,TSMatrix &Q)
{ // 求稀疏矩陣的和Q=M+N
Triple *Mp,*Me,*Np,*Ne,*Qh,*Qe;
if(M.mu!=N.mu)
return ERROR;
if(M.nu!=N.nu)
return ERROR;
Q.mu=M.mu;
Q.nu=M.nu;
Mp=&M.data[1]; // Mp的初值指向矩陣M的非零元素首地址
Np=&N.data[1]; // Np的初值指向矩陣N的非零元素首地址
Me=&M.data[M.tu]; // Me指向矩陣M的非零元素尾地址
Ne=&N.data[N.tu]; // Ne指向矩陣N的非零元素尾地址
Qh=Qe=Q.data; // Qh、Qe的初值指向矩陣Q的非零元素首地址的前一地址
while(Mp<=Me&&Np<=Ne)
{
Qe++;
switch(comp(Mp->i,Np->i))
{
case 1: *Qe=*Mp;
Mp++;
break;
case 0: switch(comp(Mp->j,Np->j)) // M、N矩陣當前非零元素的行相等,繼續比較列
{
case 1: *Qe=*Mp;
Mp++;
break;
case 0: *Qe=*Mp;
Qe->e+=Np->e;
if(!Qe->e) // 元素值為0,不存入壓縮矩陣
Qe--;
Mp++;
Np++;
break;
case -1: *Qe=*Np;
Np++;
}
break;
case -1: *Qe=*Np;
Np++;
}
}
if(Mp>Me) // 矩陣M的元素全部處理完畢
while(Np<=Ne)
{
Qe++;
*Qe=*Np;
Np++;
}
if(Np>Ne) // 矩陣N的元素全部處理完畢
while(Mp<=Me)
{
Qe++;
*Qe=*Mp;
Mp++;
}
Q.tu=Qe-Qh; // 矩陣Q的非零元素個數
return OK;
}
Status SubtSMatrix(TSMatrix M,TSMatrix N,TSMatrix &Q)
{ // 求稀疏矩陣的差Q=M-N
int i;
for(i=1;i<=N.tu;i++)
N.data[i].e*=-1;
AddSMatrix(M,N,Q);
return OK;
}
Status MultSMatrix(TSMatrix M,TSMatrix N,TSMatrix &Q)
{ // 求稀疏矩陣的乘積Q=M*N
int i,j,h=M.mu,l=N.nu,Qn=0;
// h,l分別為矩陣Q的行、列值,Qn為矩陣Q的非零元素個數,初值為0
ElemType *Qe;
if(M.nu!=N.mu)
return ERROR;
Q.mu=M.mu;
Q.nu=N.nu;
Qe=(ElemType *)malloc(h*l*sizeof(ElemType)); // Qe為矩陣Q的臨時數組
// 矩陣Q的第i行j列的元素值存於*(Qe+(i-1)*l+j-1)中,初值為0
for(i=0;i<h*l;i++)
*(Qe+i)=0; // 賦初值0
for(i=1;i<=M.tu;i++) // 矩陣元素相乘,結果累加到Qe
for(j=1;j<=N.tu;j++)
if(M.data[i].j==N.data[j].i)
*(Qe+(M.data[i].i-1)*l+N.data[j].j-1)+=M.data[i].e*N.data[j].e;
for(i=1;i<=M.mu;i++)
for(j=1;j<=N.nu;j++)
if(*(Qe+(i-1)*l+j-1)!=0)
{
Qn++;
Q.data[Qn].e=*(Qe+(i-1)*l+j-1);
Q.data[Qn].i=i;
Q.data[Qn].j=j;
}
free(Qe);
Q.tu=Qn;
return OK;
}
Status TransposeSMatrix(TSMatrix M,TSMatrix &T)
{ // 求稀疏矩陣M的轉置矩陣T。演算法5.1
int p,q,col;
T.mu=M.nu;
T.nu=M.mu;
T.tu=M.tu;
if(T.tu)
{
q=1;
for(col=1;col<=M.nu;++col)
for(p=1;p<=M.tu;++p)
if(M.data[p].j==col)
{
T.data[q].i=M.data[p].j;
T.data[q].j=M.data[p].i;
T.data[q].e=M.data[p].e;
++q;
}
}
return OK;
}
Status FastTransposeSMatrix(TSMatrix M,TSMatrix &T)
{ // 快速求稀疏矩陣M的轉置矩陣T。演算法5.2
int p,q,t,col,*num,*cpot;
num=(int *)malloc((M.nu+1)*sizeof(int)); // 生成數組([0]不用)
cpot=(int *)malloc((M.nu+1)*sizeof(int)); // 生成數組([0]不用)
T.mu=M.nu;
T.nu=M.mu;
T.tu=M.tu;
if(T.tu)
{
for(col=1;col<=M.nu;++col)
num[col]=0; // 設初值
for(t=1;t<=M.tu;++t) // 求M中每一列含非零元素個數
++num[M.data[t].j];
cpot[1]=1;
for(col=2;col<=M.nu;++col) // 求第col列中第一個非零元在T.data中的序號
cpot[col]=cpot[col-1]+num[col-1];
for(p=1;p<=M.tu;++p)
{
col=M.data[p].j;
q=cpot[col];
T.data[q].i=M.data[p].j;
T.data[q].j=M.data[p].i;
T.data[q].e=M.data[p].e;
++cpot[col];
}
}
free(num);
free(cpot);
return OK;
}
void main()
{
TSMatrix A,B;
printf("創建矩陣A: ");
CreateSMatrix(A);
PrintSMatrix(A);
FastTransposeSMatrix(A,B);
printf("矩陣B(A的快速轉置): ");
PrintSMatrix(B);
DestroySMatrix(A);
DestroySMatrix(B);
}
稀疏矩陣三元組轉置,你參考下