学习地址:http://blog.csdn.net/stpeace/article/details/8091123
#include<iostream>
using namespace std;
typedef struct LNode
{
int data;
struct LNode *next;
}LNode,*List;
List createList()//创建链表
{
LNode *head,*p1,*p2;
p1=p2=head=new LNode;//分配内存,head指的是头结点,头结点不存放数据
int a;
cin>>a;
while(0!=a)//设置一个结束标志用于创建链表
{
p1->data=a;
p2->next=p1;//这时p2是一个新节点,p1又是下一个节点
p2=p1;//把完成的节点赋给p2,使其成为一个节点
p1=new LNode;
cin>>a;
}
p2->next=NULL;
return head;
}
int getLength(List p)//求链表的长度,不包括头结点
{
int length=0;
while(NULL!=p->next)
{
length++:
p=p->next;//前移
}
return length;
}
//把元素elem插入到pos位置
List insert(List p,int pos,int elem)//向链表中插入元素
{
int length=getLength(p);//求得长度
if(pos<1||pos>length+1)//length不包括头结点,length为1即表示第一个节点
{
cout<<"error"<<endl;
exit(1);//退出
}
LNode *p1=p->next;//elem后的那个节点
LNode *p1=p;//elem前的那个节点
int i;
for(i=0;i<pos-1;i++)//链表只能一个个找
{
p2=p1;//p2在前,p1在后
p1=p1->next;
}
LNode *s=new LNode;
s->data=elem;
p2->next=s;
s->next=p1;//调整指向
return p;
}
List del(List p,int a)//删除指定值所指的节点
{
LNode *p1=NULL,p2=NULL;
if(NULL==p->next)
{
return p;//这里p是最后一个节点
}
p1=p1->next;//a的后一个节点
p2=p;//a前一个节点,刚开始时也相当于头结点
while(NULL!=p1&&a!=p1->data)
{
p2=p1;
p1=p1->next;//这两段代码实现了节点前移
}
if(NULL=p1)//表示已到最后一个节点
{
cout<<"not found"<<endl;
}
else
{
p2->mext=p1->next;
delete p1;
}
return p;
}
void release(List p)//递归释放链表
{
if(NULL==p->next)
{
delete p;
}
else
{
release(p->next);//释放节点
}
}
void Xrelease(List p)
{
List temp;//temp是指向一个结构体数据的指针,p传进来的是指向头结点的指针
while(p)
{
temp=p;
p=p->next;
delete temp;//temp是一个指针,释放p指向的那个地址
}
}
void print(List p)//打印链表
{
while(NULL!=p->next)//成立,p表示最后一个节点
{
cout<<p->next->data<<endl;
p=p->next;
}
}
//递增归并链表
void merge1(LNode *A,LNode *B,LNode *&C)//A,B,C都是头结点
{
LNode *p=A->next;//指向最小节点
LNode *q=B->next;
LNode *r;//r始终指向C的终端节点(每增加一个节点后的终端节点)
C=A;//用A的头结点做C的头结点
C->next=NULL;
free(B);//用指针指向B的第一个有效节点,然后释放头结点
r=C;
while(p!=NULL&&q!=NULL)
{
if(p->data<=q->data)//一个一个比较
{
r->next=p;p=p->next;
r=r->next;
}
else
{
r->next=q;q=q->next;
r=r->next;
}
}
r->next=NULL;
if(p!=NULL) r->next=p;//当一个链表插入完成后,另一个链表补到后面
if(q!=NULL) r->next=q;
}
//使用尾插法,用数组中的元素建立链表
List createListW(LNode *&C,int a[],int n)
{
LNode *s,*r;//s指向新申请的节点,r始终指向C的终端节点
int i;
C=new LNode;
C->next=NULL;
r=C;//r指向头结点,此时头结点就是终端节点
for(i=0;i<n;i++)
{
s=new LNode;
s->data=a[i];
r->next=s;
r=r->next;
}
r->next=NULL;
return C;
}
//利用数组元素,使用头插法建立链表,头插法从头部开始插入,得到的链表的数据将是倒过来的
List createListT(LNode &*C,int a[],int n)
{
LNode *s;
int i;
C=new LNode;
C->next=NULL;
for(i=0;i<n;i++)
{
s=new LNode;
s->data=a[i];
s->next=C->next;//s的指针域指向了C了,C->next为C的指针域
C->next=s;
}
return C;
}
//头插法实现递减
List merge5(LNode *A,LNode *B,LNode *&C)
{
LNode *p=A->next;
LNode *q=B->next;
LNode *s;
C=A;
C->next=NULL;
free(B);
while(p!=NULL&&q!=NULL)
{
if(p->data<=q->data)
{
s=p;p=p->next;
s->next=C->next;
C->next=s;
}
else
{
s=q;q=q->next;
s->next=C->next;
C->next=s;
}
}
while(q!=NULL)
{
s=q;q=q->next;
s->next=C->next;
C->next=s;
}
while(p!=NULL)
{
s=p;p=p->next;
s->next=C->next;
C->next=s;
}
return C;
}
int main()
{
List head;
head=createList();
print(head);
int a;
a=getLength(head);
int b=3;
insert(head,3,b);
int c=5;
del(head,3,b);
List head3;
List head1=createList();
List head2=createList();
merge1(head1,head2,head3);
release(head);//Xrelease(head);
List head4;
int d[5]={1,2,3,4,5};
createListW(head,d,5);
List head5;
int e[5]={4,5,6,7,8};
createListT(head5,e,5);
merge5(head1,head2,head3);
return 0;
}
那个createList的函数中,p1=new Node;这行代码应该在p1->data=a;这行代码的上面。这样头结点才不会有数据。源代码修改不方便,故在后面说一下