两分钟弄懂单链表倒置

本人真的很菜qwq,大二学数据结构的时候链表逆置就一直弄不懂,今天死磕了一下午,找了各种讲解,终于弄懂了,话不多说嘞,上题!

5.设线性表 L=(a1,a2,a…,an-2,a-1,a。)采用带头结点的单链表保存,链表中结点定义如下:

请设计一个空间复杂度为 O(1)且时间上尽可能高效的算法,重新排列 L 中的各结点,得到线性表

L'=(a1,an,a2,an-1,a3,an-2…)。要求:

1.给出算法的基本设计思想

2.根据设计思想,采用 C 或 C++语言描述算法,关键之处给出注释。

3.说明你所设计的算法的时间复杂度。

L'相比于L是将最后一个元素插入到第一个元素之后,倒数第二个元素插入到第二个元素之后...

把整个表分为前后两部分,后半部分倒置,(带头结点的倒置链表问题)倒置后从前后两部分分别取一个元素出来进行排列放置

设置两个指针p和q,指针p每次走一步,指针q走两步,这样q走到表尾,p正好在表中间,然后将L的后半段结点原地逆置,从单链表前后两端中各取一个节点,重新排列

void change_link(NODE *h)
{
    NODE *p,*q,*r,*s;
    p=q=h;//初始都在一个位置上
    while(q->next!=NULL){
    p=p->next;//p走一步
    q=q->next;//q走一步
    if(q->next!=NULL)//判断下一步不会到队尾 q走两步
        q=q->next
    }
    //循环结束之后,p指向链表的中间位置,对链表进行逆置
    q=p->next;
    p->next=NULL;//断链,让p和q之间断开
    while(q!=NULL)
    {
        r=q->next;//用r存储q的下一个结点值防止断链时造成数据混乱
        q->next=p->next;//q下一个结点的位置指向p下一个结点位置
        p->next=q;//让q成为p的下一位
        q=r;//q往后移动一位 
    }
    s=h->next;//s指向前半段的第一个数据节点,即插入点
    q=p->next;//q指向后半段的第一个结点
    p->next=NULL;//断链
    while(q!=NULL)
    {
        r=q->next;
        q->next=s->next;
        s->next=q;
        s=q->next;
        q=r;
    }
}

废话一句  诶嘿进最佳新人了乐(利韩厨走遍世界篇)

回归正题

下面是对链表逆置的详解

此处特别感谢b站up小熊学长x,我的救命恩人,好多道题都是他讲懂的,包括前面那个辅助数组,对于我这种菜鸟真的很友好!图源讲解视频

断链操作就是让p->next=NULL,也就是在4和5中间是NULL,是断开的,m指向5,n指向6

m=p->next;

n=m->next;

m->next=p->next;//看图让m的next指向p的next,也就是5->NULL

p->next=m;//这句话是让p的下一个指向m也就是5,重新连接链式结构,此时的结构也就是p->5->NULL

m=n;//让m后移一个位置到n的位置,此时m指向6,n指向7

下一次循环,m->next=p->next;此时m指向6,p->next是5,也就是让6->5实现逆置

p->next=m;p的下一个指向m,此时的结构就变成了4->6->5,实现了倒置

ok这样是不是豁然开朗!单链表逆置拿下!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值