列举了一些数据结构常用算法的代码实现及注释讲解,所有代码都自己进行过测试,如有疑问请留言。
插入排序
#include <stdio.h>
typedef struct
{
int key;
}datatype;
void D_InsertSort(datatype R[ ],int n)
/*待排序的n个元素放在数组R中,用直接插入法进行排序*/
{ int i,j;
for ( i=2; i<=n; i++) /*i控制第i-1次插入,最多进行n-1次插入*/
if (R[i].key<R[i-1].key) /*小于时,需将R[i]插入有序表*/
{ R[0]=R[i]; /*为统一算法设置监视哨*/
for ( j=i-1; R[0].key<R[j].key;j--)
R[j+1]=R[j]; /*元素后移*/
R[j+1]= R[0]; /*将放在R[0]中的第i个元素插入到有序表中*/
}
}
void ShellSort(datatype R[ ], int n, int d[ ], int t)
{ /* 按增量序列d[0], d[1]… d[t?1]对排序表R[1]..R[n]进行希尔排序,n是元素个数。注意d[0]、 d[1]、 d[2]、…、 d[t-1] 除1之外不能有公因子,且d[t-1]必须为1 */
int i,j,k,h;
for(k=0; k<t; k++)
{h=d[k]; /*本趟的增量*/
for(i=h+1; i<=n; i++)
if(R[i].key<R[i-h].key) /*小于时,需插入有序表*/
{R[0]=R[i]; /*存放待插入的记录*/
for(j=i-h;j>0&&R[0].key<R[j].key; j=j-h)
R[j+h]=R[j]; /*记录后移*/
R[j+h]=R[0]; /*插入到正确位置*/
}
}
}
void main()
{datatype a[]={0,91,67,35,62,29,72,46,57};
int i;
int d[3]={4,2,1};
D_InsertSort(a,8);
printf("\n");
for (i=1;i<=8;i++)
printf("%d ",a[i]);
ShellSort(a,8,d,3);
printf("\n");
for (i=1;i<=8;i++)
printf("%d ",a[i]);
printf("\n");
}
迪杰斯特拉算法
#include <stdio.h>
#define MaxVertexNum 100
/* 最大顶点数设为100 */
#define MaxCost 9999
/* 边的权值最大为9999 */
typedef char VertexType;
/* 顶点类型设为字符型 */
typedef int EdgeType;
/* 边的权值设为整型 */
typedef struct
{ VertexType vexs[MaxVertexNum];
/* 存放顶点信息 */
EdgeType edges[MaxVertexNum][MaxVertexNum];
/* 存放邻接关系 */
int n,e; /*顶点数和边数*/
}Mgraph;
void CreateMGraph(Mgraph *G)
{int i,j,k,w;
printf("请输入顶点数和边数(输入格式为:顶点数,边数):\n") ;
scanf("%d,%d",&(G->n),&(G->e));
printf("请输入顶点信息:\n");
for(i=0;i<G->n;i++)
scanf("\n%c",&(G->vexs[i]));
for(i=0;i<G->n;i++)
for(j=0;j<G->n;j++)
G->edges[i][j]=MaxCost;
printf("请输入每条边对应的两个顶点的序号(输入格式为:i,j,w):\n");
for(k=0;k<G->e;k++)
{ scanf("%d,%d,%d",&i,&j,&w);
G->edges[i][j]=w; }
}
void ShortestPath(Mgraph *G,int P[ ],int D[ ])
{ int final[MaxVertexNum],i,j,k,min;
final[0]=1; /* 初始时集合S中只有0号顶点 */
D[0]=0;
P[0]=-1; /* 0号顶点 无前驱顶点 ,用-1表示 */
for(i=1;i<G->n;i++)
{ final[i]=0;
D[i]=G->edges[0][i];
P[i]=0; /* P[i]存放i号顶点的前驱顶点 */
}
for(i=1;i<G->n; i++) /*重复G->n-1次*/
{ min=MaxCost;
for(k=0;k<G->n;k++)
if(final[k]==0&&D[k]<min)
{j=k;min=D[k];}
final[j]=1; /* 将顶点j加入集合S */
for(k=0;k<G->n;k++)
if(final[k]==0 && D[j]+G->edges[j][k]< D[k])
{ D[k]=D[j]+G->edges[j][k];
P[k]=j; }
}
}
void main()
{Mgraph G;
int P[MaxVertexNum],D[MaxVertexNum];
int i,pre;
CreateMGraph(&G);
ShortestPath(&G,P,D);
for(i=1;i<G.n; i++)
{ printf("%d:%d",D[i],i);
pre= P[i];
while(pre>=0)
{ printf("<-%d",pre);
pre=P[pre];
}
printf("\n");
}
}
普利姆算法
#include <stdio.h>
#define MaxVertexNum 100
/* 最大顶点数设为100 */
#define MaxCost 9999
/* 边的权值最大为9999 */
typedef char VertexType;
/* 顶点类型设为字符型 */
typedef int EdgeType;
/* 边的权值设为整型 */
typedef struct
{ VertexType vexs[MaxVertexNum];
/* 存放顶点信息 */
EdgeType edges[MaxVertexNum][MaxVertexNum];
/* 存放邻接关系 */
int n,e; /*顶点数和边数*/
}Mgraph;
void CreateMGraph(Mgraph *G)
{int i,j,k,w;
printf("请输入顶点数和边数(输入格式为:顶点数,边数):\n") ;
scanf("%d,%d",&(G->n),&(G->e));
printf("请输入顶点信息:\n");
for(i=0;i<G->n;i++)
scanf("\n%c",&(G->vexs[i]));
for(i=0;i<G->n;i++)
for(j=0;j<G->n;j++)
G->edges[i][j]=MaxCost;
printf("请输入每条边对应的两个顶点的序号(输入格式为:i,j,w):\n");
for(k=0;k<G->e;k++)
{ scanf("%d,%d,%d",&i,&j,&w);
G->edges[i][j]=w;
G->edges[j][i]=w; }
}
void Prim(int gm[][MaxVertexNum],int tree[],int cost[],int n)
{ int i,j,k,mincost,flag[MaxVertexNum];
for (i=1; i<n; i++) flag[i]=0;
flag[0]=1;/*一开始最小生成树中只有0号顶点V0,即 U 中只有V0*/
for (i=1; i<n; i++)
{ cost[i]=gm[0][i];
tree[i]=0; }
for (i=1;i<n;i++) /* 循环n-1次,每次求出最小生成树的一条边 */
{ mincost=MaxCost; k=0;
for(j=1;j<n;j++)
{if (flag[j]==0 && cost[j]<mincost)
{ mincost=cost[j];k=j;}
} /* 找出值最小的 cost[k] */
flag[k]=1;/* 将Vk加入到当前最小生成树中,即将 Vk 加入到 U 中 */
for(j=1;j<n;j++)/* 修改cost[ ]和tree[ ] */
if (flag[j]==0 && gm[k][j]<cost[j])
{ cost[j]=gm[k][j];tree[j]=k;}
}
}
void main()
{Mgraph G;
int i;
int tree[MaxVertexNum],cost[MaxVertexNum];
CreateMGraph(&G);
Prim(G.edges,tree,cost,G.n);
for (i=1;i<G.n;i++)
printf("(%d,%d),%d\n",tree[i],i,cost[i]);
/* 输出最小生成树中的每条边 */
}
佛洛依德算法
#include <stdio.h>
#define MaxVertexNum 100
/* 最大顶点数设为100 */
#define MaxCost 9999
/* 边的权值最大为9999 */
typedef char VertexType;
/* 顶点类型设为字符型 */
typedef int EdgeType;
/* 边的权值设为整型 */
typedef struct
{ VertexType vexs[MaxVertexNum];
/* 存放顶点信息 */
EdgeType edges[MaxVertexNum][MaxVertexNum];
/* 存放邻接关系 */
int n,e; /*顶点数和边数*/
}Mgraph;
void CreateMGraph(Mgraph *G)
{int i,j,k,w;
printf("请输入顶点数和边数(输入格式为:顶点数,边数):\n") ;
scanf("%d,%d",&(G->n),&(G->e));
printf("请输入顶点信息:\n");
for(i=0;i<G->n;i++)
scanf("\n%c",&(G->vexs[i]));
for(i=0;i<G->n;i++)
for(j=0;j<G->n;j++)
G->edges[i][j]=MaxCost;
printf("请输入每条边对应的两个顶点的序号(输入格式为:i,j,w):\n");
for(k=0;k<G->e;k++)
{ scanf("%d,%d,%d",&i,&j,&w);
G->edges[i][j]=w; }
}
void floyd(Mgraph G,int D[MaxVertexNum][MaxVertexNum],int P[MaxVertexNum][MaxVertexNum])
{ int i,j,k;
for(i=0;i<G.n;i++)
for(j=0;j<G.n;j++)
{D[i][j]=G.edges[i][j];
if ((D[i][j]<MaxCost)&&(D[i][j]!=0))
P[i][j]=j;
else
P[i][j]=-1;
}
for(i=0;i<G.n;i++)
D[i][i]=0;
for(k=0;k<G.n;k++)
for(i=0;i<G.n;i++)
for(j=0;j<G.n;j++)
if (D[i][j]>D[i][k]+D[k][j])
{D[i][j]=D[i][k]+D[k][j];
P[i][j]=P[i][k]; /* i到j的路径上i的后继顶点改为i到k路径上i的后继顶点 */
}
}
void opfloy(int n,int D[MaxVertexNum][MaxVertexNum],int P[MaxVertexNum][MaxVertexNum])
{int i,j,k,c,min,next;
for (i=0;i<n;i++)
{printf("\n\n源点为v%d:",i);
for (j=0;j<n;j++)
if (j!=i)
{printf("\n%d到%d最短路径:\n",i,j);
printf("%d",i);
next=P[i][j];
while (next!=-1)
{printf("->%d",next);
next=P[next][j]; }
if (D[i][j]==MaxCost)
printf("->%d",j);
printf("\t%d",D[i][j]); }
}
}
void main()
{Mgraph G;
int n,D[MaxVertexNum][MaxVertexNum],P[MaxVertexNum][MaxVertexNum];
CreateMGraph(&G);
floyd(G,D,P);
opfloy(G.n,D,P);
printf("\n");
}
克鲁斯卡尔算法
#include <stdio.h>
#define MaxVertexNum 100
/* 最大顶点数设为100 */
#define MaxEdgeNum 100
/* 最大边数设为100 */
#define MaxCost 9999
/* 边的权值最大为9999 */
typedef char VertexType;
/* 顶点类型设为字符型 */
typedef int EdgeCost;
/* 边的权值设为整型 */
typedef struct
{ VertexType vexs[MaxVertexNum];
/* 存放顶点信息 */
EdgeCost edges[MaxVertexNum][MaxVertexNum];
/* 存放邻接关系 */
int n,e; /*顶点数和边数*/
}Mgraph;
typedef struct
{ int v1;
int v2;
EdgeCost cost;
}EdgeType;
void CreateMGraph(Mgraph *G)
{int i,j,k,w;
printf("请输入顶点数和边数(输入格式为:顶点数,边数):\n") ;
scanf("%d,%d",&(G->n),&(G->e));
printf("请输入顶点信息:\n");
for(i=0;i<G->n;i++)
scanf("\n%c",&(G->vexs[i]));
for(i=0;i<G->n;i++)
for(j=0;j<G->n;j++)
G->edges[i][j]=MaxCost;
printf("请输入每条边对应的两个顶点的序号(输入格式为:i,j,w):\n");
for(k=0;k<G->e;k++)
{ scanf("%d,%d,%d",&i,&j,&w);
G->edges[i][j]=w;
G->edges[j][i]=w; }
}
void Sort(Mgraph *G, EdgeType e[],int *EdgeNum) /* 用Kruskal方法求最小生成树 */
{EdgeType e1;
int i,j,k,m;
int mincost;
m=-1;
for(i=0;i<G->n;i++)
for(j=i+1;j<G->n;j++)
if(G->edges[i][j]!=MaxCost)
{m++;
e[m].v1=i;
e[m].v2=j;
e[m].cost=G->edges[i][j];
} /*将边存入数组e中*/
for(i=0;i<m;i++)
{mincost=e[i].cost;
k=i;
for (j=i+1;j<=m;j++)
if(e[j].cost<mincost)
{mincost=e[j].cost;
k=j;
}
if (k!=i)
{e1=e[i];
e[i]=e[k];
e[k]=e1;
}
} /* 对m+1条边按权值排序 */
*EdgeNum=m+1;
}
int Find(int father[ ],int v)
/* 寻找顶点v所在树的根结点的编号 */
{ int t;
t=v;
while(father[t]>=0)
t=father[t];
return(t);
}
void Kruskal(EdgeType edges[],EdgeType T[],int m,int n)
/* 假定edges[]中的数据已按cost值由小到大排序 */
{ int father[MaxVertexNum];
int i,j,vf1,vf2;
for(i=0;i<n;i++) father[i]=-1;
i=0;j=0;
while (i<m && j<n-1)
{ vf1=Find(father,edges[i].v1);
vf2=Find(father,edges[i].v2);
if (vf1!=vf2)
/*vf1!=vf2表示两个顶点v1,v2不在一个连通分量上*/
{father[vf2]=vf1;
T[j]=edges[i];
j++;
}
i++;}
}
void main()
{Mgraph G;
EdgeType e[MaxEdgeNum],T[MaxEdgeNum];
int m,i;
CreateMGraph(&G);
Sort(&G,e,&m);
Kruskal(e,T,m,G.n);
for (i=0;i<G.n-1;i++)
printf("\n(%d,%d),%d",T[i].v1,T[i].v2,T[i].cost);
printf("\n");
}
堆排序
#include <stdio.h>
typedef int keytype;
typedef struct
{keytype key;
}datatype;
void HeapAdjust(datatype R[],int s,int t)
{ int i,j;
datatype rc;
rc=R[s]; /*用rc暂存R[S]*/
i=s; j=2*i;
for (j=2*i;j<=t;j=2*j)
{ if (j<t && R[j].key<R[j+1].key)
j=j+1;
if (rc.key>R[j].key)
break;
R[i]=R[j]; /*j号元素上移*/
i=j; /*准备继续向下调整*/
}
R[i]=rc; /*将rc中的元素放到R[i]中*/
}
void heapsort(datatype R[],int n)
{ int i;
for(i=n/2;i>=1;i--)
HeapAdjust(R,i,n);
for(i=n;i>1;i--)
{ R[0]=R[1];
R[1]=R[i];
R[i]=R[0];
HeapAdjust(R,1,i-1);
}
}
void main()
{ int i;
datatype a[]={0,1,7,9,54,33,656,342,2,2224,123};
heapsort(a,10);
for(i=1;i<=10;i++) printf("%d ",a[i]);
printf("\n");
}
二叉排序树
#include <stdio.h>
#include <stdlib.h>
#define MAXNUM 20
#define NULL 0
typedef int keytype;
typedef struct
{ keytype key; /* 关键码 */
}datatype;
typedef struct bistnode
{datatype data;
struct bistnode *lchild, *rchild;
}BiSTNode,*BiSTree;
BiSTree BST_InsertNode(BiSTree t,keytype kx)
/* 将关键码为kx的元素插入二叉排序树中 */
{ BiSTNode *f,*p,*s;
p=t;
while(p)
{ if (kx==p->data.key) {printf("kx已存在,不需插入!"); return(t);}
else { f=p;
if(kx<p->data.key) p=p->lchild;
else p=p->rchild;}
}
s=(BiSTNode *)malloc(sizeof(BiSTNode));
s->data.key=kx;
s->lchild=NULL;
s->rchild=NULL;
if (!t) t=s; /* 向空树中插入时 */
else { if(kx<f->data.key) f->lchild=s;
else f->rchild=s; }
return(t);
} /* 利用该算法便可构造一棵二叉排序*/
BiSTree BST_Creat( ) /*生成二叉排序树*/
{BiSTree t=NULL;
keytype kx;
scanf("%d",&kx); /*假设关键码是整型的*/
//scanf(… ); /*读入其它信息*/
while(kx!=0) /*假设读入0结束*/
{ t=BST_InsertNode(t,kx); /*向二叉排序树t中插入关键码为kx的结点*/
scanf("%d",&kx); /*输入下一关键码*/
//scanf(… );
}
return(t);
}
BiSTNode* BST_Search1(BiSTree t, keytype kx)
/*在二叉排序树t上查找关键码为kx的元素,若找到,返回所在结点的地址,否则返回空指针*/
{ BiSTNode *p;
p=t;
while(p) /*从根结点开始查找*/
{if (kx==p->data.key) return(p); /*kx等于当前结点p的关键码,查找成功*/
if(kx<p->data.key) p=p->lchild; /*kx小于p的关键码转左子树查找*/
else p=p->rchild; /*kx大于p的关键码转右子树查找*/
}
return NULL; /*查找失败*/
}
BiSTNode* BST_Search2 (BiSTree t, keytype kx)
{ /*在二叉排序树t上查找关键码为kx的元素,若找到,返回所在结点的地址,否则返回空指针*/
if (t==NULL || t->data.key==kx)
return(t); /*若树空,或者根结点的关键码等于kx,返回t*/
else if(kx<t->data.key)
BST_Search2(t->lchild, kx); /*kx小于p的关键码在左子树查找*/
else BST_Search2(t->rchild, kx); /*kx大于p的关键码在右子树查找*/
}
void inorder(BiSTree t)
{if(t)
{ inorder(t->lchild);
printf("%d ",t->data);
inorder(t->rchild);}
}
void main()
{BiSTree bt,p;
bt=BST_Creat( );
inorder(bt);
p=BST_Search1(bt,99);
if(p) printf("\n%d",p->data.key);
p=BST_Search2(bt,99);
if(p) printf("\n%d",p->data.key);
printf("\n");
}
广度优先搜索
#include <stdio.h>
#define MaxVertexNum 100
/* 最大顶点数设为100 */
typedef char VertexType;
/* 顶点类型设为字符型 */
typedef int EdgeType;
/* 边的权值设为整型 */
typedef struct
{ VertexType vexs[MaxVertexNum];
/* 存放顶点信息 */
EdgeType edges[MaxVertexNum][MaxVertexNum];
/* 存放邻接关系 */
int n,e; /*顶点数和边数*/
}Mgraph;
int flag[MaxVertexNum];
void CreateMGraph(Mgraph *G)
{int i,j,k;
printf("请输入顶点数和边数(输入格式为:顶点数,边数):\n") ;
scanf("%d,%d",&(G->n),&(G->e));
printf("请输入顶点信息:\n");
for(i=0;i<G->n;i++)
scanf("\n%c",&(G->vexs[i]));
for(i=0;i<G->n;i++)
for(j=0;j<G->n;j++)
G->edges[i][j]=0;
printf("请输入每条边对应的两个顶点的序号(输入格式为:i,j):\n");
for(k=0;k<G->e;k++)
{ scanf("\n%d,%d",&i,&j);
G->edges[i][j]=1;
G->edges[j][i]=1; }
}
void BFSM(Mgraph *G,int k)
/*从vk出发,广度优先遍历图G*/
{ int i,j;
int Q[MaxVertexNum],front,rear;
front=-1;rear=-1; /* 初始化队列Q */
printf("%c ",G->vexs[k]);
flag[k]=1;
rear++; Q[rear]=k; /* k入到队列Q中 */
while(front!=rear) /* 队列Q不空时 */
{ front++;i=Q[front];
for (j=0;j<G->n;j++)
if(G->edges[i][j]==1&&!flag[j])
{ printf("%c ",G->vexs[j]);
flag[j]=1;
rear++; Q[rear]=j; /* j入队 */
}
}
}
void BFSTraverseAL(Mgraph *G)
{ int i;
for (i=0;i<G->n;i++)
flag[i]=0;
/* 给所有顶点一个未被访问标记 */
for (i=0;i<G->n;i++)
if(!flag[i]) BFSM(G,i);
/*若vi未被访问过,从vi 开始进行广度优先遍历*/
} /* 要特别注意非连通图的遍历 */
void main()
{Mgraph G;
CreateMGraph(&G);
BFSTraverseAL(&G);
printf("\n");
}
深度优先搜索
#include <stdio.h>
#include <stdlib.h>
#define NULL 0
#define MaxVerNum 100
/* 最大顶点数设为100 */
typedef char vertexType;
/* 顶点类型设为字符型 */
typedef struct node
{ int adjvex;
struct node *next;
}EdgeNode;
typedef struct vnode
{ vertexType vertex;
EdgeNode *firstedge;
}VertexNode;
typedef VertexNode AdjList[MaxVerNum];
typedef struct
{ AdjList adjlist;
int n,e ;
}ALGraph;
int flag[MaxVerNum];
void CreateALGraph(ALGraph *G)
{int i,j,k;
EdgeNode *s;
printf("请输入顶点数和边数(输入格式为:顶点数,边数):\n" );
scanf("%d,%d",&(G->n),&(G->e));
printf("请输入顶点信息:\n");
for(i=0;i<G->n;i++)
{ scanf("\n%c",&(G->adjlist[i].vertex));
G->adjlist[i].firstedge=NULL;}
printf("请输入边的信息(输入格式:i,j):\n");
for(k=0;k<G->e;k++)
{scanf("%d,%d",&i,&j);
s=(EdgeNode*)malloc(sizeof(EdgeNode));
s->adjvex=j;
s->next=G->adjlist[i].firstedge;
G->adjlist[i].firstedge=s;
s=(EdgeNode*)malloc(sizeof(EdgeNode));
s->adjvex=i;
s->next=G->adjlist[j].firstedge;
G->adjlist[j].firstedge=s;}
}
void DFSAL(ALGraph *G,int i)
{ EdgeNode *p; int j;
printf("%c ",G->adjlist[i].vertex);/*访问顶点vi*/
flag[i]=1; /* 标记顶点vi已被访问过 */
p= G->adjlist[i].firstedge; /*取vi边表头指针*/
while (p) /* 若p存在 */
{ j=p->adjvex;
if ( !flag[j]) /* 若顶点 j 未被访问过 */
DFSAL(G,j);
/* 从顶点 j 出发开始深度优先遍历图 */
p=p->next; /*找和vi 相邻的下一邻接顶点*/
}
}
void DFSTraveseAL(ALGraph *G)
{ int i;
for (i=0; i<G->n;i++) flag[i]=0;
/* 给每个顶点一个未访问过标记 */
for (i=0; i<G->n; i++)
if (!flag[i]) DFSAL(G,i);
/*若顶点vi未访问过,从vi开始深度优先遍历图*/
} /* 要特别注意非连通图的遍历 */
void main()
{ALGraph G;
CreateALGraph(&G);
DFSTraveseAL(&G);
printf("\n");
}
归并排序
1.非递归
#include <stdio.h>
typedef struct
{int key;
}datatype;
void Merge ( datatype R[ ], datatype R1[ ], int s, int m, int t )
/* 将有序的 R[s..m] 和 R[m+1..t] 归并为有序的 R1 [ s..t] */
{ int i,j,k;
i=s; j = m+1; k= s;
while( i <= m && j<= t)
{ if ( R[i].key <=R[j].key ) R1[k++] = R[ i++];
else R1[k++] = R[ j++];
} /* 将 R 中的记录由小到大依次并入到 R1中 */
while ( i <= m ) R1[k++] = R[ i++]; /* 将剩余的 R[i..m] 复制到 R1中 */
while ( j <= t ) R1[k++] = R[ j++]; /* 将剩余的 R[j..t] 复制到 R1中 */
}
void MergePass(datatype R[],datatype R1[],int len,int n)
/* len是本趟归并中有序表的长度,从R[1..n]归并到R1[1..n]中 */
{ int i;
// for(i=1;i+2*len-1<=n;i+2*len) Merge(R,R1,i,i+len-1,i+2*len-1);/* 对两个长度为len的有序表进行合并 */
i=1;
while(i+2*len-1<=n)
{ Merge(R,R1,i,i+len-1,i+2*len-1);
i=i+2*len;}
if (i+len-1<n) Merge(R,R1,i,i+len-1,n);
/* 对剩下的两个有序表(后一个有序表长度小于len)进行合并 */
else
while(i<=n) R1[i++]=R[i++];
/*将剩余的最后一个有序表复制到R1中*/
}
void MergeSort(datatype R[],int n)
/* 对R进行2-路归并结果仍在R中 */
{ datatype R1[20];
int i,len=1;
while (len<n)
{ MergePass(R,R1,len,n);
/* 一趟归并结果在R1中 */
for (i=1;i<=n;i++) R[i]=R1[i];
/* 将R1[1..n] 复制到R[1..n]中,为下一步操作做准备*/
len=2*len;
}
}
void main()
{datatype a[]={0,43,56,7,4,6,2,6,111,456,42,112,12};
int i;
MergeSort(a,12);
for(i=1;i<=12;i++) printf("%d ",a[i].key);
printf("\n");
}
2.递归
#include <stdio.h>
#define maxnum 20
typedef struct
{int key;
}datatype;
void Merge(datatype R[ ], datatype R1[ ], int s, int m, int t)
/* 将有序的 R[s..m] 和 R[m+1..t] 归并为有序的 R1 [ s..t] */
{ int i,j,k;
i=s; j = m+1; k= s;
while( i <= m && j<= t)
{ if ( R[i].key <=R[j].key ) R1[k++] = R[ i++];
else R1[k++] = R[ j++];
} /* 将 R 中的记录由小到大依次并入到 R1中 */
while ( i <= m ) R1[k++] = R[ i++]; /* 将剩余的 R[i..m] 复制到 R1中 */
while ( j <= t ) R1[k++] = R[ j++]; /* 将剩余的 R[j..t] 复制到 R1中 */
}
void Msort(datatype R[ ],datatype R1[ ],int s,int t)
{ int m;
datatype R2[maxnum];
if (s==t) R1[s]=R[s];
else
{ m=(s+t)/2 ; /* 将R[s..t]分为R[s..m]和R[m+1..t] */
Msort(R,R2,s,m); /* 递归地将R[s..m]归并为有序的R2[s..m] */
Msort(R,R2,m+1, t); /* 递归地将R[m+1..t]归并为有序的R2[m+1..t] */
Merge(R2,R1,s,m,t); /* 将R2[s..m]和R2[m+1..t] 归并到R1[s..t]*/
}
}
/*void Msort(datatype R[ ],int s,int t)
{ int m,i;
datatype R1[maxnum];
if (s<t)
{ m=(s+t)/2 ;
Msort(R,s,m);
Msort(R,m+1,t);
Merge(R,R1,s,m,t);
for (i=s;i<=t;i++) R[i]=R1[i]; }
}*/
void MergeSort(datatype R[ ],datatype R1[ ],int n)
/* 将顺序表 R 进行归并排序*/
{ Msort(R,R1,1,n); }
void main()
{datatype a[ ]={0,43,56,3,22,67,1,97,-6,12,87,77,99,54,76},b[maxnum];
int i;
MergeSort(a,b,14); /* Msort(a,b,1,14); */
for(i=1;i<=14;i++)
printf("%d ",b[i].key);
printf("\n");
}
快速排序
#include <stdio.h>
typedef int keytype;
typedef struct
{ keytype key; /* 关键码 */
}datatype;
int Partition(datatype R[],int low,int high)
{ R[0]=R[low]; /* 暂存界点元素到R[0]中*/
while(low<high) /* 从表的两端交替地向中间扫描 */
{ while(low<high&&R[high].key>=R[0].key) high--;
if(low<high){R[low]=R[high];low++;}
while(low<high&&R[low].key<R[0].key) low++;
if (low<high) { R[high]=R[low]; high--;}
}
R[low]=R[0]; /* 将界点元素放到其最终位置 */
return low; /* 返回界点元素所在的位置*/
}
void Quick_Sort(datatype R[],int s,int t) /* 对R[s]到R[t]的元素进行排序 */
{ int i;
if (s<t)
{ i=Partition(R,s,t);
Quick_Sort(R,s,i-1);
Quick_Sort(R,i+1,t); }
}
void main()
{int i;
datatype a[20]={0,2,3,4,1,5,9,7,6};
Quick_Sort(a,1,8);
for (i=1;i<=8;i++)
printf("%d ",a[i]);
printf("\n");
}
哈夫曼
#include <stdio.h>
#include <stdlib.h>
#define MAXVALUE 10000 /*最大权值为10000 */
#define MAXLEAF 30 /* 最多有30个叶子结点 */
#define MAXNODE MAXLEAF*2-1
/* 因哈夫曼树无度为1的结点,总结点数
n=n0+n2 。当n0 =30时,根据二叉树性质
n0=n2+1, n2 = n0 –1=29,所以哈夫曼树
最多有30+29 =59个结点 */
#define MAXBIT 10
typedef struct
{int weight;
int parent;
int lchild;
int rchild;
}HNodeType;
typedef struct
{ int bit[MAXBIT ]; /*保存各字符哈夫曼编码的空间*/
int start; /* 保存各字符哈夫曼编码的开始位置 */
}HCodeType;
void Create_HuffMTree(HNodeType HFMTree[ ],int n)
{int m1,m2,x1,x2;
int i,j;
for(i=0;i<2*n-1;i++)
{HFMTree[i].weight=0;
HFMTree[i].parent=-1;
HFMTree[i].lchild=-1;
HFMTree[i].rchild=-1;}
for (i=0;i<n;i++)
scanf("%d",&HFMTree[i].weight);
for(i=0;i<n-1;i++)
{ x1=x2=MAXVALUE;
m1=m2=0;
for (j=0;j<n+i;j++)
{if (HFMTree[j].parent==-1&&
HFMTree[j].weight<x1)
{x2=x1;m2=m1;
x1=HFMTree[j].weight;
m1=j;}
else if(HFMTree[j].parent==-1&&
HFMTree[j].weight<x2)
{x2=HFMTree[j].weight;
m2=j;}
}
HFMTree[m1].parent=n+i;
HFMTree[m2].parent=n+i;
HFMTree[n+i].weight=
HFMTree[m1].weight+HFMTree[m2].weight;
HFMTree[n+i].lchild=m1;
HFMTree[n+i].rchild=m2;}
}
void HuffmanCode(HNodeType HFMTree[ ], HCodeType HuffCode[ ],int n)
{ HCodeType cd;
int i,j,c,p;
for(i=0;i<n;i++)
{cd.start=n-1;
c=i;
p=HFMTree[c].parent;
while(p!=-1)
{ if(HFMTree[p].lchild==c)
cd.bit[cd.start]=0;
else
cd.bit[cd.start]=1;
cd.start--;
c=p;
p=HFMTree[p].parent;
}
for (j=cd.start+1;j<n;j++)
HuffCode[i].bit[j]=cd.bit[j];
HuffCode[i].start=cd.start+1;
}
}
void main()
{HNodeType HFM[MAXNODE];
int num;
int i,j;
HCodeType HFMCode[MAXLEAF];
scanf("%d",&num);
Create_HuffMTree(HFM,num);
HuffmanCode(HFM,HFMCode,num);
for(i=0;i<num;i++)
{for (j=HFMCode[i].start;j<num;j++)
printf ("%d",HFMCode[i].bit[j]);
printf("\n");
}
}
单链表
#include <stdio.h>
#include <stdlib.h>
#define null 0
typedef int datatype;
typedef struct node
{datatype data;
struct node *next;
}LNode,*LinkList;
LNode *create_head ( )
{ LNode *head;
head = (LNode *)malloc(sizeof(LNode));
head->next = NULL;
return (head);
}
LinkList Create_LinkList1( )
{ LNode *s;
LinkList head;
int x;
head =create_head ();
scanf("%d",&x); /*假设数据域为整型*/
while(x!=-1) /*-1为结束标志*/
{s=(LNode*)malloc(sizeof(LNode)); /*为新结点申请空间*/
s->data=x; s->next=head->next; /*为新结点赋值*/
head->next=s; /*修改头指针*/
scanf("%d",&x);}
return(head);
}
LinkList Create_LinkList2( )
{ LNode *s;
LinkList head,r;
//LinkList head,r;
int x;
head =create_head ();
r=head; /*尾结点也是头结点*/
scanf("%d",&x); /*假设数据域为整型*/
while(x!=-1) /*-1为结束标志*/
{s=(LNode*)malloc(sizeof(LNode)); /*为新结点申请空间*/
s->data=x; s->next=NULL; /*为新结点赋值*/
r->next=s; /*将新结点连到表尾*/
r=s; /*修改尾指针的值*/
scanf("%d",&x);}
return head;
}
LNode *Get_LinkList(LinkList L,int i)
{ LNode *p=L;
int j=0;
while(p->next!=NULL&&j<i)
{ p=p->next; j++; }
if(j==i) return p;
else return NULL;
}
int Insert_LinkList(LinkList L,int i,datatype x)
{ LNode *p,*s;
p=Get_LinkList(L,i-1);
if(p==NULL)
{ printf("i is wrong!");
return 0;}
else
{ s=(LNode*)malloc(sizeof(LNode));
s->data=x;
s->next=p->next;
p->next=s;
return 1; }
}
int Del_LinkList(LinkList L,int i)
{ LinkList p,s;
p=Get_LinkList(L,i-1);
if(p==NULL)
{ printf("i-1 not exist!\n"); return -1; }
else if(p->next==NULL)
{ printf("i not exist!\n"); return 0; }
else
{ s=p->next;
p->next=s->next;
free(s);
return 1; }
}
void output(LNode *h)
{ LNode *p;
printf("Output:");
p=h->next;
while (p!=null)
{ printf("%d ",p->data);
p=p->next;
}
printf("\n");
}
void main()
{LNode *L2;
L2=Create_LinkList1( );
output(L2);
L2=Create_LinkList2( );
output(L2);
Insert_LinkList(L2,3,99);
output(L2);
Del_LinkList(L2,1);
output(L2);
}
顺序表
#include <stdio.h>
#include <stdlib.h>
#define maxsize 10
typedef int datatype;
typedef struct
{datatype data[maxsize];
int last;
}seqlist;
seqlist *init()
{seqlist *L;
L=(seqlist*)malloc(sizeof(seqlist));
L->last=-1;
return(L);
}
void input(seqlist *L)
{int i,k;
printf("Input element number:");
scanf("%d",&k);
for(i=0;i<=k-1;i++)
scanf("%d",&L->data[i]);
L->last=k-1;
}
void output(seqlist *L)
{int i;
printf("\noutput:");
for(i=0;i<=L->last;i++)
printf("%d ",L->data[i]);
}
int insert(seqlist *L,int i,datatype x)
{int j;
if (L->last==maxsize-1)
{printf("List full!");
return(-1); }
if (i<1||i>L->last+2)
{printf("Error!");
return(0); }
for (j=L->last;j>=i-1;j--)
L->data[j+1]=L->data[j];
L->data[i-1]=x;
L->last++;
return(1);
}
int delete(seqlist *L,int i)
{int j;
if (i<1||i>L->last+1)
{printf("No exist!");
return(0); }
for (j=i;j<=L->last;j++)
L->data[j-1]=L->data[j];
L->last--;
return(1);
}
void main()
{ seqlist *L1;
L1=init();
input(L1);
output(L1);
delete(L1,2);
output(L1);
insert(L1,3,88);
output(L1);
}
顺序队列
#include <stdio.h>
#include <stdlib.h>
#define MAXSIZE 10
typedef int datatype;
typedef struct
{ datatype data[MAXSIZE];
int front,rear;
}C_SeQueue;
C_SeQueue *Int_SeQueue( )
{ C_SeQueue *q;
q=(C_SeQueue*)malloc(sizeof(C_SeQueue));
q->front=q->rear=0; /* 或MAXSIZE-1等 */
return q;
}
int Empty_SeQueue(C_SeQueue *q)
{if(q->front ==q->rear ) return 1;
else return 0;
}
int In_SeQueue(C_SeQueue *q,datatype x)
{ if ((q->rear+1)%MAXSIZE==q->front)
{ printf("队满");
return -1; }
else
{ q->rear=(q->rear+1)%MAXSIZE;
q->data[q->rear]=x;
return 1; }
}
int Out_SeQueue(C_SeQueue *q, datatype *x)
{ if (q-> front == q->rear)
//if (Empty_SeQueue(q))
{ printf("队空");
return -1;}
else
{ q->front=(q->front+1)% MAXSIZE;
*x=q->data[q->front];
return 1; }
}
void main()
{C_SeQueue *sq;
int x;
sq=Int_SeQueue( );
printf("输入(-1结束):");
scanf("%d",&x);
while (x!=-1)
{if (In_SeQueue(sq,x)==-1) break;
scanf("%d",&x);}
while (!Empty_SeQueue(sq))
{if(Out_SeQueue(sq,&x)) printf("%d ",x);
}
}
顺序栈
#include <stdio.h>
#include <stdlib.h>
#define MAXSIZE 10
typedef int datatype;
typedef struct
{ datatype data[MAXSIZE];
int top; /* 栈顶指针 */
} SeqStack;
SeqStack *init_SeqStack( )
{ SeqStack *S;
S=(SeqStack*)malloc
(sizeof(SeqStack));
S->top=-1;
return S;
}
int Empty_SeqStack(SeqStack *S)
{ if(S->top==-1) return 1;
else return 0;
}
int Push_SeqStack(SeqStack *S,datatype x)
{if(S->top==MAXSIZE-1) return(0);
else { S->top++; S->data[S->top]=x;
return(1); }
}
int Pop_SeqStack(SeqStack *S,datatype *x)
{ if(Empty_SeqStack(S)==1) return 0;
else { *x=S->data[S->top];
S->top--;
return 1;}
}
datatype Top_SeqStack(SeqStack *S)
{ if(Empty_SeqStack(S)==1)
return 0;
else
return(S->data[S->top]);
}
void conversion1(int N,int r)
{SeqStack *s;
datatype x;
s=init_SeqStack( );
while(N)
{ Push_SeqStack(s,N%r);
N=N/r; }
while(!Empty_SeqStack(s))
{Pop_SeqStack(s,&x) ;
printf("%d",x);}
}
void conversion2(int N,int r)
{int s[10],top;
int x;
top=-1;
while(N)
{s[++top]=N%r;
N=N/r; }
while(top!=-1)
{x=s[top--];
printf("%d",x);}
}
int fact(int n) //算法功能是求解并返回n的阶乘
{
if (n==0) return(1);
else return(n*fact(n-1));
}
void main()
{
SeqStack *S;
int x;
S=init_SeqStack( );
Push_SeqStack(S,1);
Push_SeqStack(S,2);
Push_SeqStack(S,3);
printf("%d",Top_SeqStack(S));
Pop_SeqStack(S,&x);
printf("\n%d",x);
printf("\n%d",Top_SeqStack(S));
Pop_SeqStack(S,&x);
printf("\n%d",x);
printf("\n%d",Top_SeqStack(S));
printf("\n");
conversion1(3467,8);
printf("\n");
conversion2(3467,8);
printf("\n");
printf("%ld",fact(4));
}
链队列
#include <stdio.h>
#include <stdlib.h>
#define MAXSIZE 10
typedef int datatype;
typedef struct node
{ datatype data;
struct node *next;
}QNode;
typedef struct
{ QNode *front, *rear;
}LQueue;
LQueue *Init_LQueue()
{ LQueue *q;
QNode *p;
q=(LQueue*)malloc(sizeof(LQueue));
p=(QNode*)malloc(sizeof(QNode));
p->next=NULL;
q->front=q->rear=p;
return q;
}
void In_LQueue(LQueue *q,datatype x)
{ QNode *p;
p=(QNode*)malloc(sizeof(QNode));
p->data=x;
p->next=NULL;
q->rear->next=p;
q->rear=p;}
int Empty_LQueue(LQueue *q)
{ if(q->front==q->rear)
return 1;
else
return 0;
}
int Out_LQueue(LQueue *q,datatype *x)
{ QNode *p;
if(Empty_LQueue(q)==1) return 0;
else { p=q->front->next;
q->front->next=p->next;
*x=p->data;
free(p);
if(q->front->next==NULL) q->rear=q->front;
return 1; }
}
void main()
{ LQueue *lq;
int x;
lq=Init_LQueue();
printf("输入(-1结束):");
scanf("%d",&x);
while (x!=-1)
{In_LQueue(lq,x);
scanf("%d",&x);}
while (!Empty_LQueue(lq))
{if(Out_LQueue(lq,&x)) printf("%d ",x);
}
}
链栈
#include <stdio.h>
#include <stdlib.h>
#define NULL 0
typedef int datatype;
typedef struct node
{ datatype data;
struct node *next;
}StackNode,*LinkStack;
LinkStack Init_LinkStack( )
{
return NULL;
}
int Empty_LinkStack(LinkStack top)
{ if(top==NULL) return 1;
else return 0; }
LinkStack Push_LinkStack(LinkStack top,datatype x)
{ StackNode *s;
s=(StackNode*)malloc(sizeof(StackNode));
s->data=x; s->next=top;
top=s; return top;
}
LinkStack Pop_LinkStack(LinkStack top,datatype *x)
{ StackNode *p;
if (top==NULL) return NULL;
//if(Empty_LinkStack(top)) { printf("Stack Empty!");return NULL;}
else{ *x=top->data;
p=top;
top=top->next;
free(p);
return top; }
}
void main()
{ LinkStack top;
int x;
top=Init_LinkStack( );
top=Pop_LinkStack(top,&x);
top=Push_LinkStack(top,1);
top=Push_LinkStack(top,2);
top=Push_LinkStack(top,3);
top=Pop_LinkStack(top,&x);
printf("%d ",x);
top=Pop_LinkStack(top,&x);
printf("%d ",x);
top=Pop_LinkStack(top,&x);
printf("%d ",x);
}