zoukankan      html  css  js  c++  java
  • Leetcode 第132场周赛总结

    132

    1025. 除数博弈

    爱丽丝和鲍勃一起玩游戏,他们轮流行动。爱丽丝先手开局。

    最初,黑板上有一个数字 N 。在每个玩家的回合,玩家需要执行以下操作:

    • 选出任一 x,满足 0 < x < NN % x == 0
    • N - x 替换黑板上的数字 N

    如果玩家无法执行这些操作,就会输掉游戏。

    只有在爱丽丝在游戏中取得胜利时才返回 True,否则返回 false。假设两个玩家都以最佳状态参与游戏。

    示例 1:

    输入:2
    输出:true
    解释:爱丽丝选择 1,鲍勃无法进行操作。
    

    示例 2:

    输入:3
    输出:false
    解释:爱丽丝选择 1,鲍勃也选择 1,然后爱丽丝无法进行操作》。
    

    思路:动态规划,f[i]表示当数字是 i 时爱丽丝是否可以赢得比赛,如果i-j时对面赢不了比赛,f[i-j]置为1,最后返回f[N]即可

    class Solution {  
    public:
        bool divisorGame(int N) {
            vector<int> f(N+1);
    
            for(int i=1;i<N+1;i++)
            {
                f[i]=0;
                for(int j=1;j<i;j++)
                {
                    if(i%j==0)
                    {
                        if(!f[i-j]) //f[i-j]表示此时对面的状态
                        {
                            f[i] = 1;
                            break;
                        }
                    }
                }
            }
            return f[N];
        }
    };
    

    ## 1026. 节点与其祖先之间的最大差值

    给定二叉树的根节点 root,找出存在于不同节点 AB 之间的最大值 V,其中 V = |A.val - B.val|,且 AB 的祖先。

    (如果 A 的任何子节点之一为 B,或者 A 的任何子节点是 B 的祖先,那么我们认为 A 是 B 的祖先)

    示例:

    输入:[8,3,10,1,6,null,14,null,null,4,7,13]
    输出:7
    解释: 
    我们有大量的节点与其祖先的差值,其中一些如下:
    |8 - 3| = 5
    |3 - 7| = 4
    |8 - 1| = 7
    |10 - 13| = 3
    在所有可能的差值中,最大值 7 由 |8 - 1| = 7 得出。
    

    思路:

    思路: 深度优先遍历,对当前节点,分别计算当前节点值与目前最小与目前最大的差值,并记录每次遍历得到的最大差值,然后更新目前最小与目前最大。

    /**
     * Definition for a binary tree node.
     * struct TreeNode {
     *     int val;
     *     TreeNode *left;
     *     TreeNode *right;
     *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
     * };
     */
    class Solution {
    public:
        int res;
        int maxAncestorDiff(TreeNode* root) {
            res = 0;
            dfs(root,root->val,root->val);
            return res;
        }
        
        void dfs(TreeNode* root,int l,int r)
        {
            if(root==NULL) return;
            res = max(res,abs(root->val-l));
            res = max(res,abs(root->val-r));
            
            l = min(root->val,l);
            r = max(root->val,r);
            
            dfs(root->left,l,r);
            dfs(root->right,l,r);
        }
    };
    

    ## 1027. 最长等差数列

    给定一个整数数组 A,返回 A 中最长等差子序列的长度

    回想一下,A 的子序列是列表 A[i_1], A[i_2], ..., A[i_k] 其中 0 <= i_1 < i_2 < ... < i_k <= A.length - 1。并且如果 B[i+1] - B[i]( 0 <= i < B.length - 1) 的值都相同,那么序列 B 是等差的。

    示例 1:

    输入:[3,6,9,12]
    输出:4
    解释: 
    整个数组是公差为 3 的等差数列。
    

    示例 2:

    输入:[9,4,7,2,10]
    输出:3
    解释:
    最长的等差子序列是 [4,7,10]。
    

    思路:哈希表

    对数组里每一个数字都开一个哈希表,记录此数字与其他数字差值为 t 的个数。

    class Solution {
    public:
        int longestArithSeqLength(vector<int>& nums) {
            int res = 0;
            int n = nums.size();
            vector<unordered_map<int,int>> hash(n);
            for(int i=1;i<n;i++)
            {
                for(int j=0;j<i;j++)
                {
                    int t = nums[i]-nums[j];
                    hash[i][t] = hash[j][t]+1; //hash[j][t]初始为0
                    res = max(res,hash[i][t]);
                }
            }
            return res+1;
        }
    };
    

    ## 1028. 从先序遍历还原二叉树

    我们从二叉树的根节点 root 开始进行深度优先搜索。

    在遍历中的每个节点处,我们输出 D 条短划线(其中 D 是该节点的深度),然后输出该节点的值。(如果节点的深度为 D,则其直接子节点的深度为 D + 1。根节点的深度为 0)。

    如果节点只有一个子节点,那么保证该子节点为左子节点。

    给出遍历输出 S,还原树并返回其根节点 root

    示例 1:

    输入:"1-2--3--4-5--6--7"
    输出:[1,2,5,3,4,6,7]
    

    示例 2:

    输入:"1-2--3---4-5--6---7"
    输出:[1,2,5,3,null,6,null,4,null,7]
    

    示例 3:

    输入:"1-401--349---90--88"
    输出:[1,401,null,349,88,90]
    

    提示:

    • 原始树中的节点数介于 11000 之间。
    • 每个节点的值介于 110 ^ 9 之间。

    思路:做了注释,代码思路很清晰,要注意的是字符串序列需要转化成数字形式。

    /**
     * Definition for a binary tree node.
     * struct TreeNode {
     *     int val;
     *     TreeNode *left;
     *     TreeNode *right;
     *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
     * };
     */
    class Solution {
    public:
        int pos = 0; //记录当前遍历到的位置,总指针
        string T;
        inline int read_val(int p) {
            int x = 0;
            for (; p < T.length() && isdigit(T[p]); ++ p)
                x = (x * 10) + (T[p] - '0');
            return x;
        }
        TreeNode* Dfs(int dep) {
            int cur = 0; //记录 '-' 的个数,表示下一个节点的深度
            for (int j = pos; j < T.length() && T[j] == '-'; ++ j) ++ cur;
            if (cur != dep) return NULL;
            pos += cur;
            TreeNode *u = new TreeNode(read_val(pos));
            while (pos < T.length() - 1 && isdigit(T[pos])) ++ pos; //跳过第一个数字后面的数字,在函数里已经计算过了
            u -> left = Dfs(dep + 1);
            u -> right = Dfs(dep + 1);
            return u;
        }
        TreeNode* recoverFromPreorder(string S) {
            T = S; return Dfs(0);
        }
        
    };
    

    这一题代码来自这位大神:zjp-shadow
    这场周赛有两道深度优先遍历的题目,这个知识点还是非常重要的,以后也要多做点这方面的题目。

  • 相关阅读:
    BEGINNING SHAREPOINT&#174; 2013 DEVELOPMENT 第15章节--开发SP2013工作流应用程序 总结
    OpenStreetMap初探(一)——了解OpenStreetMap
    企业服务总线架构介绍
    【Stackoverflow好问题】java在,如何推断阵列Array是否包括指定的值
    C和指针 (pointers on C)——第一章:高速启动
    类别sort使用排序
    [Oracle]
    4点,从今天谈用户体验设计经验京东亚马逊购物
    从[java.lang.OutOfMemoryError: Java heap space]恢复
    C++学习笔记32 断言函数
  • 原文地址:https://www.cnblogs.com/lyc1226/p/10851489.html
Copyright © 2011-2022 走看看