关于单链表的逆置问题

大家都知道单链表是只能前结点找到后结点的,关于单链表的逆置也困扰了我很久,终于受不了了,进行了一番重新学习

在我学到的方法有这么几种:三指针法(也可以理解为辅助指针法)、头插法、今天学到的递归;

壹、三指针法:我们先来看这个理解图

这个图看上去应该可以很好的理解这种方法;

下面就是三指针法的实现:

typedef int DataType; //类型定义
typedef struct node{  //单链表定义
      DataType data;
	  struct node* next;
}LinkedNode,*LinkList;
void ReverseList(LinkList& ListHead)
{
	cout<<"Begin to Reverse the List"<<endl;
	if( (NULL==ListHead)||(NULL==ListHead->next) )return ;  //边界检测
	LinkedNode* pPre=ListHead;    //先前指针
	LinkedNode* pCur=pPre->next;  //当前指针
	LinkedNode* pNext=NULL;       //后继指针
	while(pCur!=NULL)
	{
		pNext=pCur->next;
		pCur->next=pPre;
		pPre=pCur;
		pCur=pNext;
	}
	ListHead->next=NULL;
	ListHead=pPre;        //记录下新的头结点
}

贰、下来就是头插法,这个要稍微理解一下了:是来看理解图

这么看应该就好理解一点了吧 ,就是将L结点指向B ,B结指向A,这样就可以达到逆置,之后我们来看代码

LNode *Inverse(LNode *L)
{
	LNode *p, *q;
	p = L->next;
	L->next = NULL;
	while (p != NULL)
	{
		q = p;
		p = p->next;

		q->next = L->next;
		L->next = q;
	}
	return L;
}

当然你也可以重新重建一个链表,用位结点指向然后将它delete掉这样来达到逆置 

就类似于这样来实现

叁、最后一种就是使用递归的方法,还是那个思路,我们先来看图

 

当然这个实现我学到了两种方法

我们来一一看一下;

第一种是返回值为空的办法

void ReverseList(LinkedNode* pCur,LinkList& ListHead)
{
	if( (NULL==pCur)||(NULL==pCur->next) )
	{
		ListHead=pCur;
	}
	else
	{
		LinkedNode* pNext=pCur->next;
		ReverseList(pNext,ListHead); //递归逆置后继结点
		pNext->next=pCur;            //将后继结点指向当前结点。
		pCur->next=NULL;
	}
}

第二种是返回结点l类型

LinkedNode* ReverseList(LinkedNode* pCur,LinkList& ListHead)
{
	cout<<"Begin to Reverse the List"<<endl;
	if( (NULL==pCur)||(NULL==pCur->next) )
	{
	        ListHead=pCur;
	        return pCur;
	}
	else
	{
		LinkedNode* pTemp=ReverseList(pCur->next,ListHead); //递归逆置后继结点
		pTemp->next=pCur;   //将后继结点指向当前结点
		pCur->next=NULL;
		return pCur;
	}
}

z这些方法你都可以去尝试,当然三指针法和头插法应该好理解一点。

猜你喜欢

转载自blog.csdn.net/Sherlock_Provence/article/details/86497825