标签:col false eve 防止 get 指针的指针 inf alt main
头指针或者尾指针需要改变,并且需要把改变的值带回到主程序,带回到调用处需要用的指针的指针;
当尾指针不发生改变,或者即使发生了改变也不希望带回到主程序当中就用指针;
1 链式存储结构
特点:用一组任意的存储单元存储线性表中的数据元素;这组存储单元可以使连续的也可以是不连续的;每个数据元素除了存储数据外,还要存储前驱、后继元素的地址。
每个元素包括数据域和指针域;存储数据的部分就是数据域,存储地址的部分就是指针域;
data | address |
数据域 | 指针域 |
2 单链表
n个节点按链式存储结构存储,每个节点只包含一个指针域;
2.1 线性表的单链表存储结构
typedef int DataType; typedef struct Node { DataType data; struct Node *next; }Node;
2.2 获取指定位置的元素
typedef int DataType; typedef struct Node { DataType data; struct Node *next; }Node; Node* getptr(Node* head,int pos) { Node *p=head; if(p==NULL || pos==0) { return head; } for(int i=0;p&&i<pos;i++) p=p->next; return p; } void main() { Node *head=NULL; ... Node *p=getptr(head,3); //获取第3个节点的元素 }
2.3 获取单链表中节点个数
typedef int DataType; typedef struct Node { DataType data; struct Node *next; }Node; int getSize(Node* head) { int size=0; Node *p=head; while(p) //直到p指向的节点地址域为空时,停止循环,返回size { size++; p=p->next; } return size; } void main() { Node *head=NULL; ... int len=getSize(head); //获取第3个节点的元素 }
2.4 单链表插入节点
typedef int DataType; typedef struct Node { DataType data; struct Node *next; }Node; bool insert(Node**head,int position,DataType d) { if(position<0||position>getSize(*head)) return false; Node *node=(Node*)malloc(sizeof(Node)); node->next=NULL; node->next=d; if(position==0) //if中的语句实现插入空链表或头部 { node->next=*head; *head=node; return true; } Node *p=getptr(*head,position-1); //以下5条语句实现插入中间或者尾部 Node *r=p->next; node->next=r; p->next=node; return true; } void main() { Node *head=NULL; ... insert(&head,0,10); //头部或者空表插入数据10 insert(&head,3,7); //第3个节点插入数据7 }
2.5 单链表删除
bool erase(Node **head,int pos) { if(pos<0 || pos>getSize(*head)) return false; Node *p=*head; if(pos==0) { *head=(*head)->next; free(p); //是否指针p,即删除p指向的节点 p=NULL; //节点不存在就让它为空,防止出现意外 return true; } p=getptr(*head,pos-1); Node *q=p->next; p->next=q->next; free(q); q=NULL; return true; } void main() { Node *head=NULL; insert(&head,0,10); insert(&head,0,8); insert(&head,0,3); insert(&head,0,5); erase(&head,0); erase(&head,1); }
2.6 将两个线性链表合并
void union(Node *a,Node *b) { Node *p=*a; if(p->next) p=p->next; p->next=b; } void main() { Node *ahead=NULL; Node *bhead=NULL; insert(&ahead,0,10); insert(&ahead,0,3); insert(&ahead,0,8); insert(&ahead,0,5); insert(&bhead,0,7); insert(&bhead,0,6); insert(&bhead,0,2); insert(&bhead,0,4); union(ahead,bhead); }
2.7 线性链表的倒置
void reverse(Node **head) { Node *p=*head; Node *q=p->next; if(q==NULL) return; Node *r=q->next; if(p==*head) //可以不要,最好不要 p->next=NULL; while(true) { q->next=p; if(r==NULL) { *head=q; break; } elase { p=q; q=r; r=r->next; } } } void main() { Node *head=NULL; insert(&head,0,10); insert(&head,0,3); insert(&head,0,8); insert(&head,0,8); reverse(&head); }
2.8 线性链表的遍历
void print(DataType d) { printf("%d\n",d); } void trave(Node *head,void(*fun)(DataType)) { Node *p=head; while(p) { fun(p->data); p=p->next; } } void main() { Node *head=NULL; insert(&head,0,10); insert(&head,0,3); insert(&head,0,8); insert(&head,0,8); trave(head,print); }
3 单循环链表
循环链表:
将单链表中最后一个节点的指针域由空改为指向第一个节点,使整个单链表形成一个环;
3.1 线性表的单循环列表存储结构
typedef int DataType typedef struct Node { DataType data; struct Node *next; }Node;
3.2 获取单循环链表中的节点个数
typedef int DataType typedef struct Node { DataType data; struct Node *next; }Node; int getSize(Node *rear) { int size=0; if(rear) { Node *p=rear->next; while(p!=rear) { size++; p=p->next; } size++; } return size; } void main() { Node *rear=NULL; //定义尾指针指向单链表最后一个节点,rear->next会指向头指针,相当于头指针 ... int len=getSize(rear); }
3.3 获取指定位置的元素
typedef int DataType typedef struct Node { DataType data; struct Node *next; }Node; Node *getptr(Node *rear,int pos) { if(rear==NULL) return rear; if(pos<0 || pos>=getSize(rear)) return NULL; Node *p=rear->next; for(int i=0;i<pos;i++) p=p->next; return p; } void main() { Node *rear=NULL; ... Node *p=getptr(rear,2); }
3.4 单循环链表插入节点
typedef int DataType typedef struct Node { DataType data; struct Node *next; }Node; bool insert(Node **rear,int position,DataType d) { if(position<0 || position>getSize(*head)) return false; Node *node=(Node*)malloc(sizeof(Node)); node->data=d; node->next=NULL; if(position==0) { if(*rear==NULL) { node->next=node; *rear=node; } else { node->next=(*rear)->next; (*rear)->next=node; } return true; } Node *p=getptr(*head,position-1); Node *r=p->next; node->next-r; p->next=node; if(*rear=p) { *rear=node; } return ture; } void main() { Node *rear=NULL; insert(&rear,0,10); insert(&rear,0,3); insert(&rear,0,8); insert(&rear,1,5); }
3.5 单循环列表的删除
bool erase(Node **rear,int pos) { if(*rear==NULL || pos<0 || pos>getSize(*head)) return false; Node *p=(*rear)->next; if(pos==0) { (*rear)->next=p->next; free(p); //是否指针p,即删除p指向的节点 p=NULL; //节点不存在就让它为空,防止出现意外 return true; } p=getptr(*rear,pos-1); Node *q=p->next; p->next=q->next; if(q==*rear) *rear=p; free(q); q=NULL; return true; } void main() { Node *rear=NULL; insert(&rear,0,10); insert(&rear,0,8); insert(&rear,0,3); insert(&rear,0,5); erase(&rear,0); erase(&rear,1); }
标签:col false eve 防止 get 指针的指针 inf alt main
原文地址:https://www.cnblogs.com/dongry/p/10025237.html