LeetCode | 24.两两交换链表中的节点

这次来写一下 LeetCode 的第 24 题,两两交换链表中的节点。

题目描述

题目直接从 LeetCode 上截图过来,题目如下:

image

上面的题就是 两两交换链表中的节点 题目的截图,同时 LeetCode 给出了一个函数的定义,然后要求实现链表两两交换的函数体。函数定义如下:

/**

 * Definition for singly-linked list.

 * struct ListNode {

 *     int val;

 *     struct ListNode *next;

 * };

 */

struct ListNode* swapPairs(struct ListNode* head){

}

从定义上看,是一个单链表,单链表只能顺着节点的指针依次找下去,而不能往回找。

问题分析

这个题目看似简单,其实还是有几个坑在里面的。听我慢慢道来。

先来看看,链表最初的情况,如下图:

image

最初链表的头指向第一个节点,我们首先要交换的是第一个节点和第二个节点,根据指针来看,只要让第一个节点的 next 指向第三个节点,然后让第二个节点的 next 指向第一个节点就可以了。在交换之前,首先要有一个指针(pre)指向第一个节点、还要有一个指针(cur)指向第二个节点,当然再准备一个指针(new)指向第三个节点。有了这些指针,就可以完成我们的交换了,如下图:

image

当交换完成以后,就接着移动这三个指针,进行下一次的交换。这样就构成了一个循环,怎么来判断是否循环?让 new = head,当 new 为 NULL 或者 new->next 为 NULL 的时候,就说明没有节点或者只剩一个节点了,就不用再交换了,这样循环就结束了。

以上看似完成了,其实还是有一个问题,我们接着推第二步交换试试。如下图:

image

开始第二轮交换的时候,指针的位置是这样的,然后按照前面的指针交换的方式进行交换。图下图:

image

交换完后的链表成了这个样子,但是仔细观察,不知道是否观察出了问题。我们的 4 号节点没有办法遍历到了。因为 1 号节点的指针仍然指向着 3 号节点,而经过交换,要把 4 号节点放到 3 号节点的前面。那么,也就是说,除了要完成 3 号节点和 4 号节点的交换,还要修正 1 号节点中 next 的指向。而此时,我们已经没有指针指向 1 号节点了。所以,我们增加一个指针 tmp 来指向 pre 指针就可以了,以后通过 tmp 指针的 next 来修正即可。修正后如下图:

image

当以后两个节点交换完成后,将 pre 指针赋值给 tmp 指针即可。

这样看似完成了,那么还有问题么?问题还是有的,我们的 head 指针一直指向的是 1 号节点,但是实际的链表头节点已经是 2 号节点了。当函数执行完成时,需要返回新的链表头节点,要怎么返回呢?我这里又增加了一个新的指针 result 来记录新的头节点,当循环完成以后,直接返回 result 就可以了。

上面的步骤就算完成了,几个问题其实都是我在写代码的时候遇到的。虽然步骤是完成了,但是我觉得我的代码应该还是有简化的空间的。暂时没有再去考虑了。

代码实现

上面说了那么多,其实代码反倒不是很复杂。代码如下:

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */


struct ListNode* swapPairs(struct ListNode* head){
    struct ListNode *new = head;
    struct ListNode *pre = NULL;
    struct ListNode *cur = NULL;

    // 如果链表本身就是空的,那么就直接返回好了
    if (head == NULL) {
        return head;
    }

    // 不管链表有多少节点,只要大于等于两个节点,那么新的链表头都是第二个节点
    struct ListNode *result = head;
    if (head->next != NULL) {
        result = head->next;
    }

    struct ListNode *tmp = NULL;

    while (new != NULL && new->next != NULL) {
        // 设置 pre 和 cur 的位置
        pre = new;
        cur = new->next;
        new = new->next->next;
        // 交换
        pre->next = cur->next;
        cur->next = pre;
        // 这就是在第二次以及以后交换中要修正的部分
        if (tmp != NULL) tmp->next = cur;
        // 为了修正,需要保留当前交换的前一个节点
        tmp = pre;
    }

    return result;
}

注释是我刚刚加上去的,其实自己整理了一遍,发现思路比当时写的时候清晰了许多。整理和总结真的是挺重要的。

提交结果

在写完 swapPairs 函数体后,点击右下角的 “执行代码”,然后观察 “输出” 和 “预期结果” 是否一致,一致的话就点击 “提交” 按钮。点击 “提交” 按钮后,系统会使用更多的测试用例来测试我们写的函数体,如果所有的测试用例都通过了,那么就会给出 “通过” 的字样,如果没有通过,会给出失败的那一组测试用例,我们继续修改代码。我们以上代码 “提交” 以后的截图如下:

image

我觉得在内存消耗上应该可以更小一些,我为了截这个图,重新提交了代码,在提交代码前还修改了几行代码,内存消耗也由 5.5 MB 变为了 5.4 MB,通过梳理自己还是能找到改进空间,给自己点个赞。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 216,744评论 6 502
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,505评论 3 392
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 163,105评论 0 353
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,242评论 1 292
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,269评论 6 389
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,215评论 1 299
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,096评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,939评论 0 274
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,354评论 1 311
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,573评论 2 333
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,745评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,448评论 5 344
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,048评论 3 327
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,683评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,838评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,776评论 2 369
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,652评论 2 354