链表问题——两两交换链表中的关于swap(p,q)的无效性讨论【相邻节点】

文章详细介绍了如何两两交换链表中的节点,提供了问题描述、输入输出说明以及完整的C++代码实现。同时,文章还讨论了直接使用`swap(p,q)`的无效性,并分享了参加IT培训班的利弊以及其他的自我学习途径。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

两两交换链表中的节点

问题描述

给定一个链表,两两交换其中相邻的节点,并返回交换后的链表。

你不能只是单纯的改变节点内部的值,而是需要实际的进行节点交换。

输入说明

首先输入链表长度len,然后输入len个整数,以空格分隔。

输出说明

输出格式见范例

输入范例

4
1 2 3 4

输出范例

head–>2–>1–>4–>3–>tail

题解

完整代码

问题不难,完整代码及注释如下:

#include<iostream>
#include<algorithm>
#include<vector>

using namespace std;



struct ListNode

{

    int val;

    ListNode *next;

    ListNode() : val(0), next(NULL) {}

    ListNode(int x) : val(x), next(NULL) {}

    ListNode(int x, ListNode *next) : val(x), next(next) {}

};

class Solution
{

public:

    ListNode* swapPairs(ListNode* head)
    {

        //填充本函数完成功能
        ListNode* p=head,*q,*fade_head;
        fade_head = new ListNode;
        fade_head ->next =head;
        ListNode *mark = fade_head;//direct to swap(p,q) 的前节点

        //len
        int len =0;
        while(p)
        {
            len++;
            p=p->next;
        }


        if(len >1)
        {
            //deal
            p=head;
            int tot=0;
            while(p)
            {
                tot++;
                if(tot == 2)//swap(p,q), 保证了q的存在
                {
                    //swap(p,q)
                    mark->next =p;
                    q->next = p->next;
                    p->next = q;

                    //init
                    mark = q;
                    tot=0;
                    q=p;//前面 p、q节点换位置了
                    p=q->next;

                }
                //
                q=p;
                p=p->next;
            }
        }
        head =fade_head->next;
        return head;

    }

};

ListNode *createByTail()

{

    ListNode *head;

    ListNode *p1,*p2;

    int n=0,num;

    int len;

    cin>>len;

    head=NULL;

    while(n<len && cin>>num)

    {

        p1=new ListNode(num);

        n=n+1;

        if(n==1)

            head=p1;

        else

            p2->next=p1;

        p2=p1;

    }

    return head;

}

void  displayLink(ListNode *head)

{

    ListNode *p;

    p=head;

    cout<<"head-->";

    while(p!= NULL)

    {

        cout<<p->val<<"-->";

        p=p->next;

    }

    cout<<"tail\n";

}

int main()

{

    ListNode* head = createByTail();

    head=Solution().swapPairs(head);

    displayLink(head);

    return 0;

}

关于swap(p,q)的无效性讨论

p 、 q 为相邻节点

swap()的思想出现在下面函数中,

class Solution
{

public:

    ListNode* swapPairs(ListNode* head)
    {

        //填充本函数完成功能
        ListNode* p=head,*q,*fade_head;
        fade_head = new ListNode;
        fade_head ->next =head;
        ListNode *mark = fade_head;//direct to swap(p,q) 的前节点

        //len
        int len =0;
        while(p)
        {
            len++;
            p=p->next;
        }


        if(len >1)
        {
            //deal
            p=head;
            int tot=0;
            while(p)
            {
                tot++;
                if(tot == 2)//swap(p,q), 保证了q的存在
                {
                    //swap(p,q)
                    mark->next =p;
                    q->next = p->next;
                    p->next = q;

                    //init
                    mark = q;
                    tot=0;
                    q=p;//前面 p、q节点换位置了
                    p=q->next;

                }
                //
                q=p;
                p=p->next;
            }
        }
        head =fade_head->next;
        return head;

    }

};

其中的

q->next = p->next;
p->next = q;

本想着用swap(p,q)直接偷懒,最后更新下p、q前一个结点的指向关系就ok,结果输出和输入一毛一样,原本还在纠结,p、q 交换后到底交换了什么?到底是p、q节点的内容变了,位置不变【p、q指向发生了变化】,还是内容不变,p、q位置变了【p、q节点位置发生了变化】,自嘲自己一下,交换指针我还是自己手写交换节点位置吧,交换后p、q的指向再换一下,这个思路还是熟悉的。

感受

链表题目的特殊操作,考虑的特例 空表、1、2,为什么要考虑2个节点呢?
比如在节点向后尾插,可能当前操作节点和最后一个节点重叠,出bug。

浅谈IT班

利弊如何

1)利


  • 学习专业知识
    IT培训班提供系统化的专业知识和技能培训,帮助学员全面掌握IT领域的知识,提高技能水平
  • 获得实践经验
    培训班通常会提供实际项目和实验,让学员在实际操作中学习和应用所学知识,获得真实的实践经验
  • 培养解决问题的能力
    培训班注重培养学员的解决问题的能力,通过解决实际问题,培养学员的逻辑思维和解决问题的能力
  • 学习团队合作
    培训班安排学员进行团队项目,让学员学会有效地与他人合作,增强团队协作能力
  • 接触最新技术
    IT行业发展迅速,培训班可以让学员接触到最新的技术和发展动态,保持行业敏感度
  • 职业发展机会
    完成培训班后获得证书,为求职增加优势,许多公司更愿意雇佣有相关培训经历的候选人
  • 拓展人际网络
    在培训班中结识志同道合的同学和业界专业导师,建立人际网络,有助于个人职业发展

2)弊


  • 费用
    参加培训班需要支付一定的费用,特别是一些高级和专业的培训班费用较高,可能会对学员的经济造成一定压力
  • 时间投入
    培训班通常需要学员投入大量时间学习和参与实践项目,对于有工作或其他学习任务的学员来说可能会较为繁忙
  • 质量参差不齐
    培训班市场竞争激烈,质量良莠不齐。选择不合适的培训班可能导致学到的知识和技能不符合实际需求,浪费时间和金钱
  • 自学成本
    有些人可能具备一定的自学能力,通过网络、书籍等自学也能获得一定的IT知识,避免了培训班的费用和时间投入
  • 学习负担
    对于已经有一定IT基础的学员来说,培训班可能会显得过于简单,造成学习负担不均衡

因此,参加IT培训班有许多优势,可以提高学习效果和职业竞争力,帮助学员掌握专业知识和技能。然而,选择合适的培训班很重要,需要考虑费用、时间投入和培训班的质量。对于有自学能力的学员来说,自学也是一个不错的选择。最终决策要根据个人的情况和学习目标进行权衡。

其他途径

  • 自学
    利用互联网上的丰富资源,如在线教程、文档、教学视频等,自行学习IT知识。自学需要良好的自律性和学习计划,但也能取得不错的学习效果。

  • 开放式课程
    一些大学、教育机构或在线教育平台提供开放式课程,可以免费或低费用参与学习,这些课程可以是计算机科学、编程、网络技术等方面的。

  • MOOC(大规模开放在线课程)
    MOOC平台如Coursera、edX、Udemy等提供丰富多样的计算机科学和IT相关课程,学员可以自由选择感兴趣的课程进行学习。

  • 图书阅读
    阅读IT相关的专业书籍和参考资料,可以深入了解具体领域的知识和实践经验。

  • 参与开源项目
    -积极参与开源项目,贡献自己的代码和解决问题,可以在实践中学到丰富的经验和技能。

  • 制定学习计划
    制定合理的学习计划,包括学习目标、内容、时间安排等,帮助自己有条理地学习IT知识。

  • 参加技术社区
    加入技术社区、技术论坛、开发者交流群等,与其他技术人员交流经验和学习心得。

  • 实践项目
    尝试完成一些实际项目,这有助于将理论知识应用到实际情境中,并提升解决问题的能力。

虽然上IT培训班是一种很有效的学习方式,但以上提到的方法同样能够帮助个人学到知识。最终,选择何种学习方式应该根据个人情况、学习目标和学习风格来做出决定。有些人可能适应培训班的有导师指导的学习方式,而有些人可能更喜欢自主学习和探索。重要的是找到适合自己的学习方式,不断进步和提升自己的技能。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

来杯Sherry

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值