数据结构总结

一、线性表

1、线性表的顺序存储结构

(1)线性表顺序存储结构代码:

1 #define MAXSIZE 20    
2 typedef int ElemType;
3 typedef struct
4 {
5 ElemType data[MAXSIZE];
6 int length;    // 线性表当前长度
7 } SqList;
View Code

(2)获得元素操作

 1 #define OK 1
 2 #define ERROR 0
 3 #define TRUE 1
 4 #define FALSE 0
 5 
 6 typedef int Status;
 7 
 8 // Status 是函数的类型,其值是函数结果状态代码,如OK等。
 9 // 初始条件:顺序线性表L已存在,1 <= i <= ListLength(L)
10 // 操作结果:用e返回L中第i个数据元素的值。
11 
12 Status GetElem(SqList L, int i, ElemType *e)
13 {
14     if( L.length==0 || i<1 || i>L.length )
15     {
16         return ERROR;
17     }
18     *e = L.data[i-1];
19 
20     return OK;
21 }
View Code

(3)插入操作

 1 /* 初始条件:顺序线性表L已存在,1<=i<=ListLength(L)。 */
 2 /* 操作结果:在L中第i个位置之前插入新的数据元素e,L长度+1。*/
 3 
 4 Status ListInsert(SqList *L, int i, ElemType e)
 5 {
 6     int k;
 7 
 8     if( L->length == MAXSIZE )  // 顺序线性表已经满了
 9     {
10         return ERROR;
11     }
12     if( i<1 || i>L->length+1)   // 当i不在范围内时
13     {
14         return ERROR;
15     }
16     if( i <= L->length )   // 若插入数据位置不在表尾
17     {
18         /* 将要插入位置后数据元素向后移动一位 */
19         for( k=L->length-1; k >= i-1; k-- )
20         {
21             L->data[k+1] = L->data[k];
22         }
23     }
24 
25     L->data[i-1] = e;  // 将新元素插入
26     L->length++;
27 
28     return OK;
29 }
View Code

(4)删除操作

 1 /* 初始条件:顺序线性表L已存在,1<=i<=ListLength(L) */
 2 /* 操作结果:删除L的第i个数据元素,并用e返回其值,L的长度-1 */
 3 Status ListDelete(SqList *L, int i, ElemType *e)
 4 {
 5     int k;
 6 
 7     if( L->length == 0 )
 8     {
 9         return ERROR;
10     }
11     if( i<1 || i>L->length )
12     {
13         return ERROR;
14     }
15 
16     *e = L->data[i-1];
17 
18     if( i < L->length )
19     {
20         for( k=i; k < L->length; k++ )
21         {
22             L->data[k-1] = L->data[k];
23         }
24     }
25 
26     L->length--;
27 
28     return OK;
29 }
View Code

 

2、单链表

(1)、单链表存储结构

1 typedef struct Node
2 {
3 ElemType data;      // 数据域
4 struct Node* Next;  // 指针域
5 } Node;
6 typedef struct Node* LinkList;
View Code

(2)单链表的读取

 1 /* 初始条件:顺序线性表L已存在,1<=i<=ListLength(L) */
 2 /* 操作结果:用e返回L中第i个数据元素的值 */
 3 
 4 Status GetElem( LinkList L, int i, ElemType *e )
 5 {
 6     int j;
 7     LinkList p;
 8 
 9     p = L->next;
10     j = 1;
11 
12     while( p && j<i )
13     {
14         p = p->next;
15         ++j;
16     }
17 
18     if( !p || j>i )
19     {
20         return ERROR;
21     }
22 
23     *e = p->data;
24 
25     return OK;
26 }
View Code

(3)单链表的插入

 1 /* 初始条件:顺序线性表L已存在,1<=i<=ListLength(L) */
 2 /* 操作结果:在L中第i个位置之前插入新的数据元素e,L的长度加1 */
 3 
 4 Status ListInsert(LinkList *L, int i, ElemType e)
 5 {
 6     int j;
 7     LinkList p, s;
 8 
 9     p = *L;
10     j = 1;
11 
12     while( p && j<i )   // 用于寻找第i个结点
13     {
14         p = p->next;
15         j++;
16     }
17 
18     if( !p || j>i )
19     {
20         return ERROR;
21     }
22 
23     s = (LinkList)malloc(sizeof(Node));
24     s->data = e;
25 
26     s->next = p->next;
27     p->next = s;
28 
29     return OK;
30 }
View Code

(4)单链表的删除

 1 /* 初始条件:顺序线性表L已存在,1<=i<=ListLength(L) */
 2 /* 操作结果:删除L的第i个数据元素,并用e返回其值,L的长度-1 */
 3 
 4 Status ListDelete(LinkList *L, int i, ElemType *e)
 5 {
 6     int j;
 7     LinkList p, q;
 8 
 9     p = *L;
10     j = 1;
11 
12     while( p->next && j<i )
13     {
14         p = p->next;
15         ++j;
16     }
17 
18     if( !(p->next) || j>i )
19     {
20         return ERROR;
21     }
22 
23     q = p->next;
24     p->next = q->next;
25 
26     *e = q->data;
27     free(q);
28 
29     return OK;
30 }
View Code

(5)单链表的整表创建

a.头插法

 1 /* 头插法建立单链表示例 */
 2 
 3 void CreateListHead(LinkList *L, int n)
 4 {
 5     LinkList p;
 6     int i;
 7 
 8     srand(time(0));   // 初始化随机数种子
 9 
10     *L = (LinkList)malloc(sizeof(Node));
11     (*L)->next = NULL;
12 
13     for( i=0; i < n; i++ )
14     {
15         p = (LinkList)malloc(sizeof(Node));  // 生成新结点
16         p->data = rand()%100+1;
17         p->next = (*L)->next;
18         (*L)->next = p;
19     }
20 }
View Code

b.尾插法

 1 /* 尾插法建立单链表演示 */
 2 
 3 void CreateListTail(LinkList *L, int n)
 4 {
 5     LinkList p, r;
 6     int i;
 7 
 8     srand(time(0));
 9     *L = (LinkList)malloc(sizeof(Node));
10     r = *L;
11 
12     for( i=0; i < n; i++ )
13     {
14         p = (Node *)malloc(sizeof(Node));
15         p->data = rand()%100+1;
16         r->next = p;
17         r = p;                 // 备注:初学者可能很难理解这句,重点解释。
18     }
19 
20     r->next = NULL;
21 }
View Code

(6)单链表的整表删除

 1 Status ClearList(LinkList *L)
 2 {
 3     LinkList p, q;
 4 
 5     p = (*L)->next;
 6 
 7     while(p)
 8     {
 9         q = p->next;
10         free(p);
11         p = q;
12     }
13 
14     (*L)->next = NULL;
15 
16     return OK;
17 }
View Code

 

3、静态链表

(1)线性表的静态链表存储结构

1 #define MAXSIZE 1000
2 typedef struct
3 {
4 ElemType data;  // 数据
5 int cur;        // 游标(Cursor)
6 } Component, StaticLinkList[MAXSIZE];
View Code

(2)静态链表进行初始化

 1 Status InitList(StaticLinkList space)
 2 {
 3 int i;
 4 for( i=0; i < MAXSIZE-1; i++ )
 5 space[i].cur = i + 1;
 6 
 7 space[MAXSIZE-1].cur = 0;
 8 
 9 return OK;
10 }
View Code

(3)获得空闲分量的下标

1 int Malloc_SLL(StaticLinkList space)
2 {
3 int i = space[0].cur;
4 if( space[0].cur )
5 space[0].cur = space[i].cur;
6    // 把它的下一个分量用来作为备用。
7 return i;
8 }
View Code

(4)静态链表的插入

 1 /* 在静态链表L中第i个元素之前插入新的数据元素e */
 2 
 3 Status ListInsert( StaticLinkList L, int i, ElemType e )
 4 {
 5     int j, k, l;
 6 
 7     k = MAX_SIZE - 1;    // 数组的最后一个元素
 8     if( i<1 || i>ListLength(L)+1 )
 9     {
10         return ERROR;
11     }
12 
13     j = Malloc_SLL(L);
14     if( j )
15     {
16         L[j].data = e;
17         for( l=1; l <= i-1; l++ )
18         {
19             k = L[k].cur;
20         }
21         L[j].cur = L[k].cur;
22         L[k].cur = j;
23 
24         return OK;
25     }
26 
27     return ERROR;
28 }
View Code

(5)静态链表的删除操作

 1 /* 删除在L中的第i个数据元素 */
 2 Status ListDelete(StaticLinkList L, int i)
 3 {
 4     int j, k;
 5 
 6     if( i<1 || i>ListLength(L) )
 7     {
 8         return ERROR;
 9     }
10 
11     k = MAX_SIZE - 1;
12 
13     for( j=1; j <= i-1; j++ )
14     {
15         k = L[k].cur;    // k1 = 1, k2 = 5
16     }
17 
18     j = L[k].cur;        // j = 2
19     L[k].cur = L[j].cur;
20 
21     Free_SLL(L, j);
22 
23     return OK;
24 }
25 
26 /* 将下标为k的空闲结点回收到备用链表 */
27 void Free_SLL(StaticLinkList space, int k)
28 {
29     space[k].cur = space[0].cur;
30     space[0].cur = k;
31 }
32 
33 /* 返回L中数据元素个数 */
34 int ListLength(StaticLinkList L)
35 {
36     int j = 0;
37     int i = L[MAXSIZE-1].cur;
38 
39     while(i)
40     {
41         i = L[i].cur;
42         j++;
43     }
44 
45     return j;
46 }
View Code

 

4、循环链表

(1)初始化部分

 1 /*初始化循环链表*/
 2 void ds_init(node **pNode)
 3 {
 4     int item;
 5     node *temp;
 6     node *target;
 7 
 8     printf("输入结点的值,输入0完成初始化\n");
 9 
10     while(1)
11     {
12         scanf("%d", &item);
13         fflush(stdin);
14 
15         if(item == 0)
16             return;
17 
18         if((*pNode) == NULL)
19         { /*循环链表中只有一个结点*/
20             *pNode = (node*)malloc(sizeof(struct CLinkList));
21             
22             if(!(*pNode))
23                 exit(0);
24             
25             (*pNode)->data = item;
26             (*pNode)->next = *pNode;
27         }
28         else
29         {
30             /*找到next指向第一个结点的结点*/
31             for(target = (*pNode); target->next != (*pNode); target = target->next)
32                 ;
33 
34             /*生成一个新的结点*/
35             temp = (node *)malloc(sizeof(struct CLinkList));
36 
37             if(!temp)
38                 exit(0);
39 
40             temp->data = item;
41             temp->next = *pNode;
42             target->next = temp;
43         }
44     }
45 }
View Code

(2)插入部分

 1 /*链表存储结构的定义*/
 2 typedef struct CLinkList
 3 {
 4     int data;
 5     struct CLinkList *next;
 6 }node;
 7 
 8 /*插入结点*/
 9 /*参数:链表的第一个结点,插入的位置*/
10 void ds_insert(node **pNode , int i)
11 {
12     node *temp;
13     node *target;
14     node *p;
15     int item;
16     int j = 1;
17 
18     printf("输入要插入结点的值:");
19     scanf("%d", &item);
20 
21     if(i == 1)
22     { //新插入的结点作为第一个结点
23         temp = (node *)malloc(sizeof(struct CLinkList));
24 
25         if(!temp)
26             exit(0);
27 
28         temp->data = item;
29 
30         /*寻找到最后一个结点*/
31         for(target = (*pNode); target->next != (*pNode); target = target->next)
32             ;
33 
34         temp->next = (*pNode);
35         target->next = temp;
36         *pNode = temp;
37     }
38     else
39     {
40         target = *pNode;
41 
42         for( ; j < (i-1); ++j )
43         {
44             target = target->next;
45         }  
46         
47         // target指向第三个元素的
48         
49         temp = (node *)malloc(sizeof(struct CLinkList));
50 
51         if(!temp)
52             exit(0);
53 
54         temp->data = item;
55         
56         p = target->next;
57         target->next = temp;
58         temp->next = p;
59     }
60 }
View Code

(3)删除部分

 1 /*删除结点*/
 2 void ds_delete(node **pNode, int i)
 3 {
 4     node *target;
 5     node *temp;
 6     int j = 1;
 7 
 8     if(i == 1)
 9     { //删除的是第一个结点
10         /*找到最后一个结点*/
11         for(target = *pNode; target->next != *pNode;target = target->next)
12             ;
13 
14         temp = *pNode;
15         *pNode = (*pNode)->next;
16         target->next = *pNode;
17         free(temp);
18     }
19     else
20     {
21         target = *pNode;
22 
23         for( ; j < i-1; ++j)
24         {
25             target = target->next;
26         }
27         
28         temp = target->next;
29         target->next = temp->next;
30         free(temp);
31     }
32 }
View Code

(4)返回结点所在位置

 1 /*返回结点所在位置*/
 2 int ds_search(node *pNode, int elem)
 3 {
 4     node *target;
 5     int i = 1;
 6 
 7     for(target = pNode; target->data != elem && target->next != pNode; ++i)
 8     {
 9         target = target->next;
10     }
11     
12     if(target->next == pNode) /*表中不存在该元素*/
13         return 0;
14     else
15         return i;
16 }
View Code

 

5、双向链表

(1)双向链表结点结构

1 typedef struct DualNode
2 {
3 ElemType data;
4 struct DualNode *prior;  //前驱结点
5 struct DualNode *next;   //后继结点
6 } DualNode, *DuLinkList;
View Code

(2)双向链表的插入操作

1 s->next = p;    
2 s->prior = p->prior;    
3 p->prior->next = s;    
4 p->prior = s;
View Code

(3)双向链表的删除操作

1 p->prior->next = p->next;
2 p->next->prior = p->prior;    
3 free(p);
View Code

 

 

 

 

 

二、栈

1、栈

(1)栈的顺序存储结构

1 typedef struct
2 {
3 ElemType *base;
4 ElemType *top;
5 int stackSize;
6 }sqStack;
View Code

(2)创建一个栈

1 #define STACK_INIT_SIZE 100
2 initStack(sqStack *s)
3 {
4 s->base = (ElemType *)malloc( STACK_INIT_SIZE * sizeof(ElemType) );
5 if( !s->base )
6 exit(0);
7 s->top = s->base;   // 最开始,栈顶就是栈底
8 s->stackSize = STACK_INIT_SIZE;
9 }
View Code

(3)入栈操作

 1 #define SATCKINCREMENT 10
 2 
 3 Push(sqStack *s, ElemType e)
 4 {
 5     // 如果栈满,追加空间
 6     if( s->top – s->base >= s->stackSize )
 7     {
 8         s->base = (ElemType *)realloc(s->base, (s->stackSize + STACKINCREMENT) * sizeof(ElemType));
 9         if( !s->base )
10             exit(0);
11 
12         s->top = s->base + s->stackSize;              // 设置栈顶
13         s->stackSize = s->stackSize + STACKINCREMENT; // 设置栈的最大容量
14     }
15 
16     *(s->top) = e;
17     s->top++;
18 }
View Code

(4)出栈操作

1 Pop(sqStack *s, ElemType *e)
2 {
3 if( s->top == s->base )  // 栈已空空是也
4 return;
5 *e = *--(s->top);
6 }
View Code

(5)销毁一个栈

 1 DestroyStack(sqStack *s){
 2 int i, len;
 3 len = s->stackSize;
 4 for( i=0; i < len; i++ ){
 5 free( s->base );
 6 s->base++;
 7 }
 8 s->base = s->top = NULL;
 9 s->stackSize = 0;
10 }
View Code

(6)计算栈的当前容量

1 int StackLen(sqStack s)
2 {
3 return(s.top – s.base);  // 初学者需要重点讲解
4 }
View Code

 

2、栈的链式存储结构

(1)栈的链式存储结构

 1 teypedef struct StackNode
 2 {
 3 ElemType data;    // 存放栈的数据
 4 struct StackNode *next;
 5 } StackNode, *LinkStackPtr;
 6 teypedef struct LinkStack
 7 {
 8 LinkStackPrt top;    // top指针
 9 int count;        // 栈元素计数器
10 }
View Code

(2)进栈操作

1 Status Push(LinkStack *s, ElemType e)
2 {
3 LinkStackPtr p = (LinkStackPtr) malloc (sizeof(StackNode));
4 p->data = e;
5 p->next = s->top;
6 s->top = p;
7 s->count++;
8 return OK;
9 }
View Code

(3)出栈操作

 1 Status Pop(LinkStack *s, ElemType *e)
 2 {
 3 LinkStackPtr p;
 4 if( StackEmpty(*s) )  // 判断是否为空栈
 5 return ERROR;
 6 *e = s->top->data;
 7 p = s->top;
 8 s->top = s->top->next;
 9 free(p);
10 s->count--;
11 return OK;
12 }
View Code

 

 

 

 

 

 

 

三、队列

1、队列

(1)创建一个队列

1 initQueue(LinkQueue *q)
2 {
3 q->front=q->rear=(QueuePtr)malloc(sizeof(QNode));
4 if( !q->front )
5         exit(0);
6 q->front->next = NULL;
7 }
View Code

(2)入队列操作

 1 InsertQueue(LinkQueue *q, ElemType e)
 2 {
 3 QueuePtr p;
 4 p = (QueuePtr)malloc(sizeof(QNode));
 5 if( p == NULL )
 6 exit(0);
 7 p->data = e;
 8 p->next = NULL;
 9 q->rear->next = p;
10 q->rear = p;
11 }
View Code

(3)出队列操作

 1 DeleteQueue(LinkQueue *q, ELemType *e)
 2 {
 3 QueuePtr p;
 4 if( q->front == q->rear )
 5 return;
 6 p = q->front->next;
 7 *e = p->data;
 8 q->front->next = p->next;
 9 if( q->rear == p )
10 q->rear = q->front;
11 free(p);
12 }
View Code

(4)销毁一个队列

1 DestroyQueue(LinkQueue *q)
2 {
3 while( q->front ) {
4 q->rear = q->front->next;
5 free( q->front );
6 q->front = q->rear;
7 }
8 }
View Code

 

2、循环队列

(1)定义一个循环队列

1 #define MAXSIZE 100
2 typedef struct
3 {
4 ElemType *base; // 用于存放内存分配基地址
5             // 这里你也可以用数组存放
6 int front;
7 int rear;
8 }
View Code

(2)初始化一个循环队列

1 initQueue(cycleQueue *q)
2 {
3 q->base = (ElemType *) malloc (MAXSIZE * sizeof(ElemType));
4 if( !q->base )
5 exit(0);
6 q->front = q->rear = 0;
7 }
View Code

(3)入队列操作

1 InsertQueue(cycleQueue *q, ElemType e)
2 {
3 if( (q->rear+1)%MAXSIZE == q->front )
4 return; // 队列已满
5 q->base[q->rear] = e;
6 q->rear = (q->rear+1) % MAXSIZE;
7 }
View Code

(4)出队列操作

1 DeleteQueue(cycleQueue *q, ElemType *e)
2 {
3 if( q->front == q->rear )
4 return ; // 队列为空
5 *e = q->base[q->front];
6 q->front = (q->front+1) % MAXSIZE;
7 }
View Code

 

 

 

 

四、递归

1、斐波那契数列的递归实现

 1  /*
 2       0,当n=0
 3 F(n) =   1,当n=1
 4          F(n-1)+F(n-2),当n>1
 5 */
 6 int Fib(int i)
 7 {
 8     if( i < 2 )
 9         return i == 0 ? 0 : 1;
10     return Fib(i-1) + Fib(i-2);
11 }
View Code

2、计算n的阶乘n!

 1   /*
 2       1            n = 0
 3 n! = 
 4           n*(n-1)    n > 0
 5 */
 6 
 7 int  factorial( n )
 8 {
 9 if( 0 == n )    return 1;
10 else   return  n * factorial( n - 1 );
11 }
View Code

3、实现将输入的任意长度的字符串反向输出的功能。

 1 /*
 2 将“#”作为一个输入结束的条件。
 3 */
 4 void print()
 5 {
 6     char a;
 7     scanf(“%c”, &a);
 8 if( a !=‘#’)  print();
 9 if( a !=‘#’)  printf(“%c”, a);
10 }
View Code

 

 

 

 

五、字符串

(1)BF算法

有两个字符串S和T,长度为N和M。首先S[1]和T[1]比较,若相等,则再比较S[2]和T[2],一直到T[M]为止;若S[1]和T[1]不等,则T向右移动一个字符的位置,再依次进行比较。

 1 // 返回子串T在主串S中第pos个字符之后的位置
 2 // 若不存在,则返回0
 3 // T非空,1 <= pos <= strlen(S)
 4 // 注意:我们这里为了表述方便,字符串使用了第一个元素表示长度的方式。
 5 
 6 int index( String S, String T, int pos )
 7 {
 8     int i = pos;    // i用于主串S中当前位置下标
 9     int j = 1;        // j用于子串T中当前位置下标
10     
11     while( i <= S[0] && j <= T[0] )    // i或j其中一个到达尾部即终止搜索!
12     {
13         if( S[i] == T[i] )    // 若相等则继续下一个元素匹配
14         {
15             i++;
16             j++;
17         }
18         else                // 若失配则j回溯到第一个元素从新匹配
19         {
20             i = i-j+2;        // i回溯到上次匹配首位的下一个元素,这是效率低下的关键!
21             j = 1;
22         }
23     }
24     
25     if( j > T[0] )
26     {
27         return i - T[0];
28     }
29     else
30     {
31         return 0;
32     }
33 }
View Code

 

 

 

 

六、数

1、双亲表示法

 1 // 树的双亲表示法结点结构定义
 2 #define MAX_TREE_SIZE 100
 3 
 4 typedef int ElemType;
 5 
 6 typedef struct PTNode
 7 {
 8     ElemType data;    // 结点数据
 9     int parent;        // 双亲位置
10 }PTNode;
11 
12 typedef struct
13 {
14     PTNode nodes[MAX_TREE_SIZE];
15     int r;            // 根的位置
16     int n;            // 结点数目
17 }PTree;
View Code

 2、孩子表示法

 1 #define MAX_TREE_SIZE     100
 2 
 3 typedef char ElemType;
 4 
 5 // 孩子结点
 6 typedef struct CTNode
 7 {
 8     int child;                // 孩子结点的下标
 9     struct CTNode *next;    // 指向下一个孩子结点的指针
10 } *ChildPtr;
11 
12 // 表头结构
13 typedef struct
14 {    
15     ElemType data;            // 存放在树中的结点的数据
16     int parent;                // 存放双亲的下标
17     ChildPtr firstchild;    // 指向第一个孩子的指针
18 } CTBox;
19 
20 // 树结构
21 typedef struct
22 {
23     CTBox nodes[MAX_TREE_SIZE];    // 结点数组
24     int r, n;
25 }
View Code

3、孩纸兄弟表示法

1 /*
2 孩纸兄弟表示法
3 */
4 typedef struct CSNode
5 {
6     TElemType data;
7     struct CSNode *firstchild,*rightsib;//第一个孩纸,和它右边的孩纸
8 }CSNode,*CSTree;
View Code

 4、二叉树的儿茶链表结点结构定义

1 /*
2 二叉树的二叉链表结点结构定义
3 */
4 
5 typedef struct BiTNode
6 {
7     TElemType data;//结点数据
8     struct BiTNode *lchild,*rchild;//左右孩纸
9 }BiTNode,*BiTree;
View Code

5、二叉树前序遍历法

 1 /*
 2 二叉树前序遍历法
 3 */
 4 void PreOrderTraverse(BiTree T)
 5 {
 6     if(T==ULL)
 7         return;
 8 
 9     printf("%c",T->data);//显示结点数据,可以更改为其他队结点操作
10 
11     PreOrderTraverse(T->lchild);//再先序遍历左子树
12 
13     PreOrderTraverse(T->rchild);//最后先序右子树
14 
15 }
View Code

6、二叉中序遍历算法

 1 /*
 2 二叉树中序遍历算法
 3 */
 4 
 5 void InOrderTraverse(BiTree T)
 6 {
 7     if(T==NULL)
 8         return;
 9 
10     InOrderTraverse(T->lchild);//中序遍历左子树
11 
12     printf("%c",T->data);//显示节点数据,可以更改为其他对结点操作
13 
14     InOrderTraverse(T->rchild);//最后中序遍历右子树
15 }
View Code

 7、二叉后序遍历算法

 1 /*
 2 二叉后序遍历递归算法
 3 */
 4 
 5 void PostOrderTraverse(BiTree T)
 6 {
 7     if(T==NULL)
 8         return;
 9 
10     PostOrderTraverse(T->lchild)//先后序遍历左子树
11 
12     PostOrderTraverse(T->rchild);//再后序遍历右子树
13 
14     printf("%c",T->data);//显示结点数据,可以更改为其他对结点操作
15 
16 }
View Code

 8、二叉树的建立

 1 /*
 2 二叉树的建立,按前序输入二叉树中结点的值,#表示空树链表表示二叉数T
 3 */
 4 void CreateBiTree(BiTree *T)
 5 {
 6     TElemType ch;
 7     scanf("%c",&ch);//输入字符串
 8 
 9     if(ch=='#')//如果是空树
10        *T=NULL;
11 
12     else
13     {
14         *T=(BiTree)malloc(sizeof(BiTNode));//获取空间
15 
16         if(!*T)
17             exit(OVERFLOW);
18 
19         (*T)->data=ch;//生成根结点
20         CreateBiTree(&(*T>lhild);//构造左子树
21         CreateBiTree(&(*T>rhild);//构造右子树
22     }
23 
24 }
View Code

 9、线索二叉树结构定义

 1 /*
 2 线索二叉树结构定义
 3 */
 4 
 5 typedef enum
 6 {
 7     Link,//Link==0表示指向左右孩纸指针
 8     Thread//Thread==1表示指向前驱或后继的线索
 9 }PointerTag;
10 
11 typedef struct BitThrNode
12 {
13     TElemType data;//结点标志
14     struct BiThrNode *lchilde,*rchild;//左右孩纸指针
15     PointerTag LTag;
16     PointerTag RTag;//左右标志
17 }BitThrNode,*BitThrTree;
View Code

10、中序遍历线索化的递归函数

 1 /*
 2 中序遍历线索化的递归函数
 3 */
 4 void InThreading(BiThrTree p)
 5 {
 6     if(p)
 7     {
 8         InTreading(p->lchild);//递归左子树线索花
 9 
10         if(!p->lchild)//没有左孩纸
11         {
12             p->LTag=Thread;//前驱线索
13             p->child=pre;//左孩纸指针指向前驱
14         }
15 
16         if(!pre->rchild)//没有右孩纸
17         {
18             pre->RTag=Thread;//后继线索
19             pre->rchild=p;//前驱右孩纸指针指向后继
20         }
21 
22         pre=p;//保持pre指向p的前驱
23 
24         InThreading(p->rchild);//递归右子树线索化
25 
26     }
27 }
View Code

11、遍历

 1 /*
 2 T指向头结点,头结点左链lchild指向根结点,头结点右链rchild指向中序遍历的,最后一个结点。
 3 中序遍历二叉线索链表表示的二叉树T
 4 */
 5 
 6 
 7 Status InOrderTraverse_Thr(BiThrTree T)
 8 {
 9     BiThrTree p;
10     p=T->child;//p指向根结点
11 
12     while(p!=T)//空树或遍历结束时,p==T
13     {
14         while(p->LTag==Link)//当LTag==0时循环到中序序列第一个节点
15             p=p->lchild;
16 
17         printf("%c",p->data);//显示结点数据,可以更改为其他对结点操作
18 
19         while(p->RTag==Thread && p->rchild!=T)
20         {
21             p=p->rchild;
22             printf("%c",p->data);
23         }
24 
25         p=p->child;//p进至其右子树根
26     }
27 
28     return OK;
29 }
View Code

 

posted @ 2015-07-12 10:11  如风轻逸  阅读(217)  评论(0编辑  收藏  举报