hot100打卡——day01

160. 相交链表

https://leetcode.cn/problems/intersection-of-two-linked-lists/description/?envType=problem-list-v2&envId=2cktkvj&

java 复制代码
/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) {
 *         val = x;
 *         next = null;
 *     }
 * }
 */
public class Solution {
    public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
        ListNode pA = headA;
        ListNode pB = headB;

        // 双指针
        while(pA != pB) {
           if (pA == null) pA = headB;
           else pA = pA.next;

           if (pB == null) pB = headA;
           else pB = pB.next;
        }
       return pA;
    }
}

如果两个链表有相交的话,可以拆分成a\b\c三段,然后初始化两个指针分别遍历两个链表,遍历完当前链表就跳到另外一个链表

那么就有结论:两指针按照上面的方式遍历,最后一定会相交于相交点或是null

可能会有人有疑惑就是,你这里判断pA != pB就进行遍历,那么要是前面的a和b部分一样长,会不会最后两指针在null相遇,错过相交点?

其实不会,如果a和b长度相等,那么不需要跳转就能直接找到了,可以模拟一下

236. 二叉树的最近公共祖先

https://leetcode.cn/problems/lowest-common-ancestor-of-a-binary-tree/description/?envType=problem-list-v2&envId=2cktkvj&

java 复制代码
/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode(int x) { val = x; }
 * }
 */
class Solution {
     public TreeNode lowestCommonAncestor(TreeNode root, TreeNode p, TreeNode q) {
        // pq都在左子树/都在右子树/分别在左右
        return dfs(p, q, root);
    }


    TreeNode dfs(TreeNode p, TreeNode q, TreeNode curNode) {
        if (curNode == null) return null;
        if (curNode == p || curNode == q) return curNode;
        TreeNode left = dfs(p, q, curNode.left);
        TreeNode right = dfs(p, q, curNode.right);

        // 不在当前子树
        if (right == null && left == null) return null;
        // 都在右子树
        if (left == null) return right;
        // 都在左子树
        if (right == null) return left;
        // 分别在左右
        return curNode;
    }
}

这道题比较抽象,对于这类递归类的题目,最好不要去模拟,而是从全局的角度看 ,比如这里为什么是后序遍历,因为对于一个节点是否是最近公共祖先,完全取 决于它的左右子树 中能否找到p和q,所以我们一进来就是判断到当前点是否是p或q中的一个,如果是的话就直接将这个点返回出去,如果不是,就要递归左右子树,并且判断。那么到这里就有四种可能p、q 在当前树的 左子树/右子树/分别在左右/压根不在当前子树,按照情况进行返回就行

234. 回文链表

https://leetcode.cn/problems/palindrome-linked-list/description/?envType=problem-list-v2&envId=2cktkvj

java 复制代码
/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode() {}
 *     ListNode(int val) { this.val = val; }
 *     ListNode(int val, ListNode next) { this.val = val; this.next = next; }
 * }
 */
class Solution {
    public boolean isPalindrome(ListNode head) {

        // 找到中点
        ListNode slow = head;
        ListNode fast = head.next;

        while(fast != null && fast.next != null) {
            slow = slow.next;
            fast = fast.next.next;
        }
        
        // 反转
        ListNode rev = rev(slow.next);
        
        ListNode p1 = head;
        ListNode p2 = rev;
        
        while (p2 != null) {
            if (p1.val != p2.val) return false;
            p1 = p1.next;
            p2 = p2.next;
        }
        return true;
    }
    
    ListNode rev(ListNode head) {
        ListNode pre = null;
        ListNode cur = head;
        while (cur != null) {
            ListNode tmp = cur.next;
            cur.next = pre;
            pre = cur;
            cur = tmp;
        }
        return pre;
    }
}

这里使用的思路就是先用快慢指针找到后半段链表的起点,然后对后半段进行反转,然后再用双指针进行遍历

739. 每日温度

java 复制代码
class Solution {
    public int[] dailyTemperatures(int[] temperatures) {
        // 单调栈,存储下标
        Deque<Integer> stack = new LinkedList<>();
        stack.push(0);
        int n = temperatures.length;
        int[] ans = new int[n];
        for (int i = 1; i < n; i++) {
            while(!stack.isEmpty() && temperatures[i] > temperatures[stack.peek()]) {
                int t = stack.pop();
                ans[t] = i - t;
            }
            stack.push(i);
        }
        return ans;
    }
}

这道题可以很明显的看到需要使用单调栈来处理,单调栈能解决的问题其实很有限,主要是用在求最近一个小于/大于当前元素的元素

这里就维护一下单调栈,每次遍历到一个元素大于当前栈顶元素的话,就将栈顶元素出栈,并且确定栈顶元素的下一个大于它的元素所隔的天数

相关推荐
千金裘换酒1 天前
LeetCode 二叉树的最大深度 递归+层序遍历
算法·leetcode·职场和发展
爱敲代码的TOM1 天前
详解一致性哈希算法
算法·哈希算法
lzllzz231 天前
递归的理解
算法·深度优先·图论
小O的算法实验室1 天前
2024年IEEE TITS SCI2区TOP,考虑无人机能耗与时间窗的卡车–无人机协同路径规划,深度解析+性能实测
算法·论文复现·智能算法·智能算法改进
派森先生1 天前
排序算法-选择排序
算法·排序算法
C雨后彩虹1 天前
书籍叠放问题
java·数据结构·算法·华为·面试
ghie90901 天前
GPS抗干扰算法MATLAB实现
开发语言·算法·matlab
格林威1 天前
基于轮廓特征的工件分类识别:实现无模板快速分拣的 8 个核心算法,附 OpenCV+Halcon 实战代码!
人工智能·数码相机·opencv·算法·目标跟踪·分类·数据挖掘
Jasmine_llq1 天前
《UVA11181 条件概率 Probability|Given》
数据结构·算法·深度优先搜索(dfs)·剪枝(可行性剪枝)·组合枚举(递归暴力枚举)·条件概率统计与归一化
老鼠只爱大米1 天前
LeetCode算法题详解 560:和为K的子数组
算法·leetcode·前缀和·哈希表·子数组求和·subarraysum