LeetCode234:回文链表

Posted TiercelChow

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了LeetCode234:回文链表相关的知识,希望对你有一定的参考价值。

题目描述

题目链接
请判断一个链表是否为回文链表。

示例 1:
输入: 1->2
输出: false

示例 2:
输入: 1->2->2->1
输出: true

进阶:
你能否用 O(n) 时间复杂度和 O(1) 空间复杂度解决此题?

解题思路

翻转前半部分链表,而后与后半部分比较判断该链表是否位回文链表

代码&注释

代码

/**
 * Definition for singly-linked list.
 * struct ListNode 
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) 
 * ;
 */
class Solution 
public:
    bool isPalindrome(ListNode* head) 
        ListNode* q = head, * cur = head, * pre = NULL, * tmp;
        while (q && q->next) 
            q = q->next->next;
            tmp = cur->next;
            cur->next = pre;
            pre = cur;
            cur = tmp; 
        
        if(q) cur = cur->next;
        while(cur) 
            if (pre->val == cur->val) 
                cur = cur->next;
                pre = pre->next;
            
            else return false;
        
        return true;
    
;

解释

  • q指针的前进速度是cur指针的两倍,当q指针指向了该链表的末尾时则表示链表的前半部分已经翻转完成。
  • 翻转过程:首先让tmp存储cur指针指向的下一个地址。然后让cur指向其前一个元素,即pre,然后pre和cur分别后移一位,完成传递,这样pre为cur原来的地址,而cur赋上tmp的值,即cur原来的地址的下一个地址,然后循环,便完成链表的循环,且修改后产生两个链表,一个是以pre为头指针的前一部分元素的翻转链表,另一个是以cur为头指针的剩余部分链表。
  • 对于链表元素个数n为奇数时,q指针指向的为最后一个元素,此时cur指针指向的元素为第(n + 1) / 2个,而反转的元素仅是前(n - 1) / 2个,因此需要将cur后移一位,再进行比较。
  • 而链表元素个数n为偶数时,在第一个while循环的最后一次循环中,q指针开始是指向链表的倒数第二个元素,因此在执行q = q->next->next时,q指向NULL,此时pre指针和cur指针分别指向第n / 2 和 n / 2 + 1个元素,直接比较即可。
  • 比较过程中规中矩,就不多赘述了。
  • 当然最妥当的情况时在比较结束之后将链表还原,还原同样是翻转,工程中应避免对源数据进行不必要的修改。

其他解法

本题同样可以通过将链表读入数组,通过双指针进行判断即可,但此法空间复杂度为O(n)
详细参考:LeetCode官网

后话

题目本身并不难也并不复杂,奈何本人过菜。尤其是指针链表方面,或许以后还会更新题解吧😀[滑稽]

以上是关于LeetCode234:回文链表的主要内容,如果未能解决你的问题,请参考以下文章

Leetcode 234. 回文链表(进阶)

链表15:回文链表的7种解法

[算法] leetcode单链表相关题目详解

leetcode 234 回文链表

LeetCode 234. 回文链表

LeetCode234. 回文链表