数据结构学习记录-矩阵的快速转置

现在发现自己的编程有了很大的提高,设计程序的速度比以前快多了,思想也有了比较大的进步,我想数据结构需要有一个严谨的逻辑思维吧!这是一个矩阵转置的程序,所有的都是自己编写的,虽然有点乱,但我觉得自己已经在慢慢进步了!!!

定义包含头文件的文件,名为t11.h

#include"stdio.h"
#include"string.h"
#include"ctype.h"
#include"malloc.h"
#include"stdlib.h"  //atoi(),exit();
#include"io.h"      //eof()
#include"math.h"


#define  TRUE  1
#define  FALSE  0
#define  OK   1
#define  ERROR 0

typedef int Status;
typedef int Boolean;

 

之后定义数据类型,名为jz.h

typedef struct
{
 int *elem;
 int i;
 int j;
 int size;
 int fz;
}jz;

struct node
{
 int i;
 int j;
 int data;
};

typedef struct
{
 node *ptr;
 int col;
 int lie;
 int geshu;
}san;

 

定义实现函数名为jz.cpp

 

jz initjz(jz &L)       //   初始化矩阵
{  
 jz R;
    printf("输入矩阵的行和列:");
 scanf("%d%d",&L.i,&L.j);
 L.size=L.i*L.j;
 L.elem=(int*)malloc(L.size*sizeof(int));    //  开辟存入矩阵内存单元
 R.elem=(int*)malloc(L.size*sizeof(int));    //  开辟转置矩阵内存单元
 int i=0;
 while(i<L.size)            //  将矩阵值全部置为0
 {
  *(L.elem+i)=0;
  *(R.elem+i)=0;
  i++;
 }
 return R;         //  将R返回
 
}

void shuru(jz &L)              //  矩阵的初始化,输入值
{
 int i,j,data;
 char ch='y';
 printf("输入矩阵的非0元,行号、列号、元素值:");
 scanf("%d%d%d",&i,&j,&data);
    *(L.elem+(i-1)*L.j+j-1)=data;
 L.fz=1;                         //   输入非零值的个数
 printf("是否继续(y/n):");
 getchar();
 ch=getchar();
 while('y' == ch || 'Y' == ch)
 {
  printf("输入矩阵的非0元的行号、列号、元素值:");
  scanf("%d%d%d",&i,&j,&data);
  *(L.elem+(i-1)*L.j+j-1)=data;
  L.fz++;
  printf("是否继续(y/n):");
  getchar();
  ch=getchar();
 }
 // printf("fz=%d\n",L.fz);
}

void cunsan(jz L,san &T)     //  将矩阵中的非零值,行号、列号存入到三元表中
{
 T.col=L.i;
 T.lie=L.j;
 T.geshu=L.fz;
 int i=1,j,k=0;
 
 T.ptr=(struct node*)malloc(L.fz*sizeof(struct node));   //  开辟存储三元表的大小
 
 while(i<=L.i)      //   寻找非零元
 {
  j=1;
  while(j<=L.j)
  {
   if(0 != *(L.elem+(i-1)*L.j+j-1))
   {
    (T.ptr+k)->i=i;
    (T.ptr+k)->j=j;
    (T.ptr+k)->data=*(L.elem+(i-1)*L.j+j-1);
    k++;
   }
   j++;
  }
  i++;
 }
 
}

void zhuanzhi(jz L,san T,san &Q)
{
 //printf("转置函数进入啦!\n");
 // getchar();
    int*p,*q,k,r;
 p=(int*)malloc(T.lie*sizeof(int));             //  构造两个辅助空间,p记录每一列的非零元的个数
 q=(int*)malloc(T.lie*sizeof(int));             //  q记录每一列的第一个非零元的位置,p第一列有3个非零元,第二列有1个非零元,q第一次为1,第二次为4
    Q.ptr=(struct node*)malloc(L.fz*sizeof(struct node));  //  开辟转置后的三元表空间内存
 int i=0;
 for(;i<T.lie;i++)               //  将开辟的空间值置0
  *(p+i)=0;
 //printf("输出值1:%d \n",*(p+i)=0);
 for(i=0;i<T.geshu;i++)          //  查找稀疏三元表中得列号,p+(T.ptr+i)->j-1) 表示(T.ptr+i)->j的列号相同指针指向内存空间,取得该地址的值加1,表示对应列又有一个元素
  
  ++(*(p+(T.ptr+i)->j-1));
 
 
 //printf("输出值:%d \n",*(p+(T.ptr+i)->j-1));
 
 *q=1;
 for(i=1;i<T.lie;i++)      //  查找稀疏三元表,知道列号,就能够将其存入到指定位置,
  *(q+i)=*(q+i-1)+(*(p+i-1));  //  辅助q,第一个为1,下一列的起始位置要加上前面的个数,*(p+i-1)表示该列在转置稀疏三元表中得位置
 for(i=0;i<T.geshu;i++)      //  依次往下查找列号
 {
        k=(T.ptr+i)->j;        //  将列号赋给k
        r=*(q+k-1);            //  将k对应的列号,在q中查找k列对应的起始位置
  (Q.ptr+r-1)->i=(T.ptr+i)->j;    //  找到起始位置,将对应的值存入
  (Q.ptr+r-1)->j=(T.ptr+i)->i;
        (Q.ptr+r-1)->data=(T.ptr+i)->data;
  ++(*(q+k-1));        //  q中对应的下一个位置就要下移一个
 }
    Q.col=T.lie;
 Q.lie=T.col;
 Q.geshu=T.geshu;
}

void print(jz L,san T,san Q,jz &R)    // 打印输出
{
 
    int i=0;
 R.size=L.size;
 printf("矩阵为:\n\t\t\t");
 while(i<L.size)
 {
  printf("%-4d",*(L.elem+i));
  if((i+1)%L.j == 0)
   printf("\n\n\t\t\t");
  i++;
 }
 printf("稀疏三元矩阵为:\n");
 i=0;
 while(i<L.fz)
 {
  printf("\t\t\t%-4d%-4d%-4d\n\n",(T.ptr+i)->i,(T.ptr+i)->j,(T.ptr+i)->data);
  i++;
 }
 printf("转置后的稀疏三元矩阵为:\n");
 i=0;
 while(i<L.fz)
 {
  printf("\t\t\t%-4d%-4d%-4d\n\n",(Q.ptr+i)->i,(Q.ptr+i)->j,(Q.ptr+i)->data);
  *(R.elem+((Q.ptr+i)->i-1)*Q.lie+(Q.ptr+i)->j-1)=(Q.ptr+i)->data;
  i++;
 }
 printf("转置矩阵为:\n");
    i=0;
 printf("\t\t\t");
 while(i<R.size)
 {
  printf("%-4d",*(R.elem+i));
  if((i+1)%Q.lie == 0)
   printf("\n\n\t\t\t");
  i++;
 }
   
 printf("\n");
 
}

 

最后就是主函数的调用了,文件名为main_jz.cpp

 

#include"t11.h"
#include"jz.h"
#include"jz.cpp"

void main()
{
 jz S,R;  //  定义两个矩阵
 san T,Q; //  定义两个三元表
 R=initjz(S);  // 分别对矩阵初始化
 shuru(S);     //  输入矩阵非零元
 cunsan(S,T);   //  将非零元存入稀疏三元表中
 zhuanzhi(S,T,Q);  // 快速转置
 print(S,T,Q,R);   // 打印输出
}

这是我自己独立设计的第5个实验了,所有代码构建都是自己完成的,在设计的过程中,跟着自己的思想,很快就把完整程序编写出来了,我相信自己的编程水平已经有了很大的提升,只要不怕困难,敢于专研奋斗,会有自己的一片天地!献给共同奋斗路上的编程朋友。。。。留住最真的于2012.03.24.22:58写~~~~~~~~~~~~~~~~~

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
稀疏矩阵是指大部分元素都为零的矩阵,因此在实现稀疏矩阵转置时,只需要对非零元素进行操作即可。以下是两种常用的方法: 方法一:三元组存储法 三元组存储法是一种常用的稀疏矩阵存储方法,将稀疏矩阵中的非零元素按行、列、值的顺序依次存储。在进行矩阵转置时,只需要将三元组中的行列互换即可。 具体实现如下: ```c typedef struct { int row; // 行 int col; // 列 int value; // 非零元素的值 } triple; void transpose(triple a[], triple b[]) { int m, n, t; // m为原矩阵的行数,n为原矩阵的列数,t为非零元素的个数 int col, p, q; // col为转置矩阵的列数,p为矩阵a的当前列,q为矩阵b的当前位置 m = a[0].row; n = a[0].col; t = a[0].value; b[0].row = n; b[0].col = m; b[0].value = t; if (t) { q = 1; for (col = 0; col < n; col++) { for (p = 1; p <= t; p++) { if (a[p].col == col) { b[q].row = a[p].col; b[q].col = a[p].row; b[q].value = a[p].value; q++; } } } } } ``` 方法二:十字链表存储法 十字链表存储法是一种更加高效的稀疏矩阵存储方法,其中每个非零元素都有一个节点,节点之间通过行、列指针相互连接。在进行矩阵转置时,只需要将每个节点的行、列指针互换即可。 具体实现如下: ```c typedef struct node { int row, col, value; struct node *right, *down; } node, *pnode; void transpose(pnode *a, pnode *b) { int m, n, t; int i, j; pnode p, q, r, s; m = (*a)->row; n = (*a)->col; t = (*a)->value; (*b) = (pnode) malloc(sizeof(node)); (*b)->row = n; (*b)->col = m; (*b)->value = t; (*b)->right = (*b)->down = (*b); if (t) { p = (*a)->right; for (i = 0; i < n; i++) { (*b)->down = (pnode) malloc(sizeof(node)); (*b)->down->right = (*b)->down->down = (*b)->down; (*b)->down->row = i; r = (*b)->down; for (j = 0; j < t; j++) { if (p->col == i) { q = (pnode) malloc(sizeof(node)); q->row = p->col; q->col = p->row; q->value = p->value; r->right = q; r = q; } p = p->right; } r->right = (*b)->down; } } } ``` 以上两种方法都能够有效地实现稀疏矩阵转置,具体实现方法可以根据实际情况选择。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值