IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 数据结构与算法 -> 算法——判断回文链表 -> 正文阅读

[数据结构与算法]算法——判断回文链表

最近在学习一些算法相关的知识,遇到回文链表,接下来将讲解三种不同的方式解回文链表

先创建一个 Node 类

public class Node {
  public int value;
  public Node next;
  public Node(int value) {
    this.value = value;
  }
}

方法一

我们知道单链表是有一个 next 指针指向下一个节点,末尾的节点指向 null,我们首先借助栈来判断是否时回文链表
栈最主要的特点:先进后出
实现思路:

  1. 遍历链表,依次将链表的节点入栈
  2. 再次遍历链表,将栈中节点一次弹栈
    1. 如果每一次遍历的节点与弹栈的节点相同,说明是回文链表
    2. 如果在遍历过程中有一次不同,那么就不是回文链表

代码演示

public static boolean isPalindrome1(Node head) {
  if (head == null || head.next == null) {
    return true;
  }
  Stack<Node> stack = new Stack<>();
  Node cur = head;
  // 将链表中所有的节点入栈
  while (cur != null) {
    stack.push(cur);
    cur = cur.next;
  }
  cur = head;
  while (cur != null) {
  // 判断链表中的节点与弹栈的节点是否相同
    if (cur.value != stack.pop().value) {
      return false;
    }
    cur = cur.next;
  }
  return true;
}

方法二

使用快慢指针 + 栈的方式
既然方法一中已经有栈的方法了,那么方法二中为什么还要使用栈呢?原因:方法一中是将所有的链表节点压入栈中,方法二是将一半的节点压入栈中。

实现思路:

  1. 首先使用快慢指针找到中间节点
  2. 将中间节点的右边压入栈
  3. 将栈中的节点一次弹栈,同时从头遍历节点,两者进行节点比较
    1. 若判断节点全部相同,则说明是回文链表,否是不是回文链表

代码演示

public static boolean isPalindrome2(Node head) {
  if (head == null || head.next == null) {
    return true;
  }
  Node slow = head.next;
  Node fast = head;
// 找到中间节点 即 slow 对应的节点
  while (fast.next != null && fast.next.next != null) {
    slow = slow.next;
    fast = fast.next.next;
  }
  Stack<Node> stack = new Stack<>();
  // 将慢指针指走向最后一个节点
  while (slow != null) {
    stack.push(slow);
    slow = slow.next;
  }
  slow = head;
  // 依次弹栈进行比较
  while (!stack.empty()) {
    if (slow.value != stack.pop().value) {
      return false;
    }
    slow = slow.next;
  }
  return true;
}

补充:

在利用快慢指针的时候,我们知道如果链表的长度是奇数个,那么慢指针将会指向最中间的节点,如果是偶数个,慢指针将会指向最中间两个的左边哪个。当我们在面试的时候如果要使用快慢指针,那么慢指针针对题目要求走到那一步更为合适,是指向最中间还是最中间的左边,亦或是最中间的右边,这都需要我们在下面多家练习,练习多了自然在面试中遇到不会出现问题

方法三

使用快慢指针 + 反转链表的方式。降低空间复杂度 O(1)

实现思路:

  1. 使用快慢指针遍历一遍链表,此时慢指针指向链表重点的位置
  2. 将慢指针右边的链表进行反转,指向中间节点,中间节点指向 null
  3. 从左右两端进行链表遍历并进行等值判断
  4. 将原来链表还原成原来的样子

代码实现

/*
	1->2->3<-2<-1
          ?
         null
*/
public static boolean isPalindrome3(Node head) {
  if (head== null || head.next == null) {
    return true;
  }
  Node n2 = head;
  Node n1 = head;
  // 使用快慢指针遍历一遍链表
  while (n2.next != null && n2.next.next != null) {
    n2 = n2.next.next;
    n1 = n1.next;
  }
  n2 = n1.next;
  n1.next = null;
  Node n3 = null;
  while (n2 != null) {  // 将右边的部分进行反转
    n3 = n2.next;
    n2.next = n1;
    n1 = n2;
    n2 = n3;
  }
  // 此时 n1 将会指向左边的一个节点
  n3 = n1;    // 保存一下 最左边的节点
  n2 = head;
  boolean res = true;
  while (n1 != null && n2 != null) {
    if (n1.value != n2.value) {
      res = false;
      break;
    }
    n1 = n1.next;
    n2 = n2.next;
  }
  // 将链表再进行还原
  n1 = n3.next;
  n3.next = null;
  while (n1 != null) {
    n2 = n1.next;
    n1.next = n3;
    n3 = n1;
    n1 = n2;
  }
  return res;
}

说明:
上面的代码中,有两次用到了反转链表这个块的知识。我们在刷一些算法题的过程中,有时候也会遇到反转链表1和反转链表2,但是那些就明明白白的告诉你就是一道反转链表的题目。
但是有时候将反转链表的思想利用的其他的算法中,成为解题的一小步的话,那么我们还能不能很好的利用反转链表这块的知识了。也会我们想得到但也并不能很好的给题目解出来。因此经典的基础题目还深入理解透彻,并能轻轻松松的写出来,才可以达到在面试时遇到算法以至于不那么被动

像在接一些比较难的题目的时候,需要用到经典的小思想,就比如上面的反转链表,我称这种为半成品,多掌握一些半成品,并能熟练运用非常有用。

  数据结构与算法 最新文章
【力扣106】 从中序与后续遍历序列构造二叉
leetcode 322 零钱兑换
哈希的应用:海量数据处理
动态规划|最短Hamilton路径
华为机试_HJ41 称砝码【中等】【menset】【
【C与数据结构】——寒假提高每日练习Day1
基础算法——堆排序
2023王道数据结构线性表--单链表课后习题部
LeetCode 之 反转链表的一部分
【题解】lintcode必刷50题<有效的括号序列
上一篇文章      下一篇文章      查看所有文章
加:2022-05-09 12:59:06  更:2022-05-09 13:01:03 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 3:20:24-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码