LeetCode - 按标签分类刷题(双指针题解)

本文汇总了多个LeetCode算法题目,包括无重复字符最长子串、盛最多水的容器、旋转链表、合并两个有序数组、验证回文串、环形链表检测与定位、判断子序列以及含退格字符串比较。通过Java实现,涵盖了字符串处理、数组操作、链表操作等核心算法知识。

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

3. 无重复字符的最长子串

在这里插入图片描述

    public int lengthOfLongestSubstring(String s) {
        int left = 0, right = 0, max = 0;
        Set<Character> set = new HashSet<>();
        while (right < s.length()) {
            if (set.contains(s.charAt(right))) {
                set.remove(s.charAt(left++));
            } else {
                set.add(s.charAt(right++));
                max = Math.max(max, set.size());
            }
        }
        return max;
    }

参考题解

11. 盛最多水的容器

在这里插入图片描述
在这里插入图片描述

public class Solution {
    public int maxArea(int[] height) {
        int l = 0, r = height.length - 1;
        int ans = 0;
        while (l < r) {
            int area = Math.min(height[l], height[r]) * (r - l);
            ans = Math.max(ans, area);
            if (height[l] <= height[r]) {
                ++l;
            }
            else {
                --r;
            }
        }
        return ans;
    }
}

61. 旋转链表

给定一个链表,旋转链表,将链表每个节点向右移动 k 个位置,其中 k 是非负数。

示例 1:

输入: 1->2->3->4->5->NULL, k = 2
输出: 4->5->1->2->3->NULL
解释:
向右旋转 1 步: 5->1->2->3->4->NULL
向右旋转 2 步: 4->5->1->2->3->NULL
示例 2:

输入: 0->1->2->NULL, k = 4
输出: 2->0->1->NULL
解释:
向右旋转 1 步: 2->0->1->NULL
向右旋转 2 步: 1->2->0->NULL
向右旋转 3 步: 0->1->2->NULL
向右旋转 4 步: 2->0->1->NULL

在这里插入图片描述
思路

先将链表闭合成环
找到相应的位置断开这个环,确定新的链表头和链表尾

算法

找到旧的尾部并将其与链表头相连 old_tail.next = head,整个链表闭合成环,同时计算出链表的长度 n。
找到新的尾部,第 (n - k % n - 1) 个节点 ,新的链表头是第 (n - k % n) 个节点。
断开环 new_tail.next = None,并返回新的链表头 new_head。

class Solution_61 {
    public ListNode rotateRight(ListNode head, int k) {

        if(head == null) return null;
        if (head.next == null) return head;

        //闭合链表
        int n;
        ListNode old_tail = head;
        for (n = 1; old_tail.next != null; n++) {
            old_tail = old_tail.next;
        }
        old_tail.next = head;

        //找到新的头节点,新的尾节点
        //新的头节点 : (n - k % n - 1);新的尾节点: (n- k % n)
        ListNode new_tail = head;
        for (int i = 0; i < n - k%n - 1; i++) {
            new_tail = new_tail.next;
        }
        ListNode new_head = new_tail.next;

        //打破闭合链表
        new_tail.next = null;

        return new_head;
    }
}

88. 合并两个有序数组

给你两个有序整数数组 nums1 和 nums2,请你将 nums2 合并到 nums1 中,使 nums1 成为一个有序数组。

说明:

初始化 nums1 和 nums2 的元素数量分别为 m 和 n 。
你可以假设 nums1 有足够的空间(空间大小大于或等于 m + n)来保存 nums2 中的元素。

示例:

输入:
nums1 = [1,2,3,0,0,0], m = 3
nums2 = [2,5,6], n = 3

输出:[1,2,2,3,5,6]

class Solution_88 {
    public void merge(int[] nums1, int m, int[] nums2, int n) {
        int[] nums1_copy = new int[m];
        System.arraycopy(nums1,0,nums1_copy,0,m);
        int first = 0;
        int second = 0;
        int count = 0;
        while ((first < m) && (second < n)){
            if (nums1_copy[first] > nums2[second]){
                nums1[count] = nums2[second];
                second++;
            }else {
                nums1[count] = nums1_copy[first++];
            }
            count++;

        }
        if (first < m){
            System.arraycopy(nums1_copy,first,nums1,first+ second,m + n - first -second);
        }
        if (second < n){
            System.arraycopy(nums2,second,nums1,first+ second,m + n - first - second);
        }

    }
}

125. 验证回文串

在这里插入图片描述

    public boolean isPalindrome(String s) {
        if (s.isEmpty())
            return true;
        int left = 0, right = s.length() - 1;
        while (left < right) {
            while (left < right && !Character.isLetterOrDigit(s.charAt(left)))
                left++;
            while (left < right && !Character.isLetterOrDigit(s.charAt(right)))
                right--;
            if (Character.toLowerCase(s.charAt(left)) != Character.toLowerCase(s.charAt(right)))
                return false;
            left++;
            right--;
        }
        return true;
    }

141. 环形链表

在这里插入图片描述
在这里插入图片描述
快慢指针方法题解:


public class Solution {
    public boolean hasCycle(ListNode head) {
        if (head == null || head.next == null) {
            return false;
        }
        ListNode slow = head;
        ListNode fast = head.next;
        while (slow != fast) {
            if (fast == null || fast.next == null) {
                return false;
            }
            slow = slow.next;
            fast = fast.next.next;
        }
        return true;
    }
}

142. 环形链表 II

在这里插入图片描述
在这里插入图片描述

public class Solution {
    public ListNode detectCycle(ListNode head) {
        ListNode fast = head, slow = head;
        while (true) {
            if (fast == null || fast.next == null) return null;
            fast = fast.next.next;
            slow = slow.next;
            if (fast == slow) break;
        }
        fast = head;
        while (slow != fast) {
            slow = slow.next;
            fast = fast.next;
        }
        return fast;
    }
}

392. 判断子序列

在这里插入图片描述
双指针方法题解:

class Solution {
    public boolean isSubsequence(String s, String t) {
        int sx = 0,tx = 0;
        int slen = s.length(),tlen = t.length();
        while(sx < slen && tx < tlen){
            if(s.charAt(sx) == t.charAt(tx)){
                sx++;
            }
            tx++;
        }
        return sx == slen;
    }
}

844. 比较含退格的字符串

在这里插入图片描述

class Solution {
    public boolean backspaceCompare(String S, String T) {
        int i = S.length() - 1, j = T.length() - 1;
        int skipS = 0, skipT = 0;

        while (i >= 0 || j >= 0) {
            while (i >= 0) {
                if (S.charAt(i) == '#') {
                    skipS++;
                    i--;
                } else if (skipS > 0) {
                    skipS--;
                    i--;
                } else {
                    break;
                }
            }
            while (j >= 0) {
                if (T.charAt(j) == '#') {
                    skipT++;
                    j--;
                } else if (skipT > 0) {
                    skipT--;
                    j--;
                } else {
                    break;
                }
            }
            if (i >= 0 && j >= 0) {
                if (S.charAt(i) != T.charAt(j)) {
                    return false;
                }
            } else {
                if (i >= 0 || j >= 0) {
                    return false;
                }
            }
            i--;
            j--;
        }
        return true;
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值