链表翻转----逆置链表的变形

具体题目详解:
给出一个链表和一个数k,比如链表1→2→3→4→5→6,k=2,翻转后2→1→4→3→6→5,若k=3,翻转后3→2→1→6→5→4,若k=4,翻转后4→3→2→1→5→6,
解决思路:
先分析题目,当节点数有K个时,逆置长度为K的链表,当节点数不足K时,则不做任何处理。
总的思路为:将长度为K的子链表从原链表中拿出,然后逆置,最后将逆置后的子链表再连接回原链表中。
我的解决方法是:编写辅助的两个函数,一个是链表逆置的。另一个是获得链表最后一个的。
具体代码如下:


//断开K长的链表,逆置后,再插回原链表中
Node* RotateList(Node* pHead, size_t k)
{
  Node* pNewHead=NULL;
  int pos=0;
  Node* pLastNode=NULL;
  Node* pNextNode=NULL;
  Node* pCur=pHead;
  pHead=NULL;
  while(pCur)
  {
    pos=0;
    pNewHead=pCur;//指向每次需要逆置的头结点
    while(pCur && pos<k-1)
    {
        pCur=pCur->next;
        pos++;
    }
    //如果pCur为空退出循环,说明不够K个节点,所以不用逆置
    if(pCur)
    {
        //保存取出链表的下一个节点,然后断开该段链表
        pNextNode=pCur->next;//保证逆置后连到原链表中
        pCur->next=NULL;

        if(NULL!=pLastNode)
            pLastNode->next=NULL;
        //逆置该段链表
        pNewHead=reverse_list(pNewHead);
        //放回原链表中
        if(NULL==pHead)//第一次逆置走这
            pHead=pNewHead;
        else//后来走这
            pLastNode->next=pNewHead;

         //获得该段链表的最后一个节点
        pCur=get_last_node(pNewHead);

        pCur->next=pNextNode;
        pLastNode=pCur;//保存最后一个节点
        pCur=pNextNode;//继续下一段链表

    }
    else
        break;

  }
  return pHead;
}
//采用头插法逆置链表
Node* reverse_list(Node* pHead)
{
  Node* pNewHead=NULL;
  Node* pCur=pHead;
  Node* pNext=NULL;
  if(NULL==pHead)
      return NULL;
  pNext=pCur->next;
  while(pNext)
  {
      pCur->next=pNewHead;
      pNewHead=pCur;
      pCur=pNext;
      pNext=pNext->next;
  }
  pCur->next=pNewHead;
  pNewHead=pCur;
  return pNewHead;
}
//获得链表中最后一个节点
Node* get_last_node(Node* pHead)
{
 Node* pCur=pHead;
 if(NULL==pHead)
     return NULL;
 while(pCur->next)
     pCur=pCur->next;
 return pCur;
}

总结:链表翻转,思路简单,但是编写代码过程中,细节较多,需要注意。比如说,取出链表时,要保存它的前一个节点和后一个节点,保证逆置后,可以放回到原链表中。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值