LeetCode 每日一题 Day 62 - 75

1686. 石子游戏 VI

Alice 和 Bob 轮流玩一个游戏,Alice 先手。

一堆石子里总共有 n 个石子,轮到某个玩家时,他可以 移出 一个石子并得到这个石子的价值。Alice 和 Bob 对石子价值有 不一样的的评判标准 。双方都知道对方的评判标准。

给你两个长度为 n 的整数数组 aliceValues 和 bobValues 。aliceValues[i] 和 bobValues[i] 分别表示 Alice 和 Bob 认为第 i 个石子的价值。

所有石子都被取完后,得分较高的人为胜者。如果两个玩家得分相同,那么为平局。两位玩家都会采用 最优策略 进行游戏。

请你推断游戏的结果,用如下的方式表示:

如果 Alice 赢,返回 1 。
如果 Bob 赢,返回 -1 。
如果游戏平局,返回 0 。

示例 1:

输入:aliceValues = [1,3], bobValues = [2,1]
输出:1
解释:
如果 Alice 拿石子 1 (下标从 0开始),那么 Alice 可以得到 3 分。
Bob 只能选择石子 0 ,得到 2 分。
Alice 获胜。
示例 2:

输入:aliceValues = [1,2], bobValues = [3,1]
输出:0
解释:
Alice 拿石子 0 , Bob 拿石子 1 ,他们得分都为 1 分。
打平。
示例 3:

输入:aliceValues = [2,4,3], bobValues = [1,6,7]
输出:-1
解释:
不管 Alice 怎么操作,Bob 都可以得到比 Alice 更高的得分。
比方说,Alice 拿石子 1 ,Bob 拿石子 2 , Alice 拿石子 0 ,Alice 会得到 6 分而 Bob 得分为 7 分。
Bob 会获胜。

提示:

n == aliceValues.length == bobValues.length
1 <= n <= 1e5
1 <= aliceValues[i], bobValues[i] <= 100

贪心做法:

class Solution {
public:
    int stoneGameVI(vector<int>& aliceValues, vector<int>& bobValues) {
        int n = aliceValues.size();
        vector<pair<int, int>> diff(n);

        for (int i = 0; i < n; ++i) {
            diff[i] = {aliceValues[i] + bobValues[i], i};
        }

        sort(diff.begin(), diff.end(), greater<pair<int, int>>());

        int aliceScore = 0, bobScore = 0;

        for (int i = 0; i < n; ++i) {
            int idx = diff[i].second;
            if (i % 2 == 0) {
                aliceScore += aliceValues[idx];
            } else {
                bobScore += bobValues[idx];
            }
        }

        if (aliceScore > bobScore) {
            return 1;
        } else if (aliceScore < bobScore) {
            return -1;
        } else {
            return 0;
        }
    }
};

1690. 石子游戏 VII

石子游戏中,爱丽丝和鲍勃轮流进行自己的回合,爱丽丝先开始 。

有 n 块石子排成一排。每个玩家的回合中,可以从行中 移除 最左边的石头或最右边的石头,并获得与该行中剩余石头值之 和 相等的得分。当没有石头可移除时,得分较高者获胜。

鲍勃发现他总是输掉游戏(可怜的鲍勃,他总是输),所以他决定尽力 减小得分的差值 。爱丽丝的目标是最大限度地 扩大得分的差值 。

给你一个整数数组 stones ,其中 stones[i] 表示 从左边开始 的第 i 个石头的值,如果爱丽丝和鲍勃都 发挥出最佳水平 ,请返回他们 得分的差值 。

示例 1:

输入:stones = [5,3,1,4,2]
输出:6
解释:

  • 爱丽丝移除 2 ,得分 5 + 3 + 1 + 4 = 13 。游戏情况:爱丽丝 = 13 ,鲍勃 = 0 ,石子 = [5,3,1,4] 。
  • 鲍勃移除 5 ,得分 3 + 1 + 4 = 8 。游戏情况:爱丽丝 = 13 ,鲍勃 = 8 ,石子 = [3,1,4] 。
  • 爱丽丝移除 3 ,得分 1 + 4 = 5 。游戏情况:爱丽丝 = 18 ,鲍勃 = 8 ,石子 = [1,4] 。
  • 鲍勃移除 1 ,得分 4 。游戏情况:爱丽丝 = 18 ,鲍勃 = 12 ,石子 = [4] 。
  • 爱丽丝移除 4 ,得分 0 。游戏情况:爱丽丝 = 18 ,鲍勃 = 12 ,石子 = [] 。
    得分的差值 18 - 12 = 6 。
    示例 2:

输入:stones = [7,90,5,1,100,10,10,2]
输出:122

提示:

n == stones.length
2 <= n <= 1000
1 <= stones[i] <= 1000

博弈DP 没有思路参考了题解:

class Solution {
    int p[1010], q[1010];
    int f[1010][1010];

public:
    int stoneGameVII(vector<int>& a) {
        int n = a.size();
        for (int i = 1; i <= n; i++)
            p[i] = a[i - 1], q[i] = q[i - 1] + p[i];
        for (int i = 1; i <= n; i++)
            f[i][i] = p[i];
        for (int i = n; i >= 1; i--) {
            for (int j = i + 1; j <= n; j++) {
                int x = q[j] - q[i];
                int y = q[j - 1] - q[i - 1];
                f[i][j] = min(p[i] + x - f[i + 1][j], p[j] + y - f[i][j - 1]);
            }
        }
        return q[n] - f[1][n];
    }
};

292. Nim 游戏

你和你的朋友,两个人一起玩 Nim 游戏:

桌子上有一堆石头。

  • 你们轮流进行自己的回合, 你作为先手 。
  • 每一回合,轮到的人拿掉 1 - 3 块石头。
  • 拿掉最后一块石头的人就是获胜者。
  • 假设你们每一步都是最优解。请编写一个函数,来判断你是否可以在给定石头数量为 n 的情况下赢得游戏。如果可以赢,返回 true;否则,返回 false 。

示例 1:

输入:n = 4
输出:false
解释:以下是可能的结果:

  1. 移除1颗石头。你的朋友移走了3块石头,包括最后一块。你的朋友赢了。
  2. 移除2个石子。你的朋友移走2块石头,包括最后一块。你的朋友赢了。
    3.你移走3颗石子。你的朋友移走了最后一块石头。你的朋友赢了。
    在所有结果中,你的朋友是赢家。

示例 2:

输入:n = 1
输出:true

示例 3:

输入:n = 2
输出:true

实际上是一个数学题(博弈论?):

class Solution {
public:
    bool canWinNim(int n) {
        return n % 4 != 0;
    }
};

1696. 跳跃游戏 VI

给你一个下标从 0 开始的整数数组 nums 和一个整数 k 。

一开始你在下标 0 处。每一步,你最多可以往前跳 k 步,但你不能跳出数组的边界。也就是说,你可以从下标 i 跳到 [i + 1, min(n - 1, i + k)] 包含 两个端点的任意位置。

你的目标是到达数组最后一个位置(下标为 n - 1 ),你的 得分 为经过的所有数字之和。

请你返回你能得到的 最大得分 。

示例 1:

输入:nums = [1,-1,-2,4,-7,3], k = 2
输出:7
解释:你可以选择子序列 [1,-1,4,3] (上面加粗的数字),和为 7 。
示例 2:

输入:nums = [10,-5,-2,4,0,3], k = 3
输出:17
解释:你可以选择子序列 [10,4,3] (上面加粗数字),和为 17 。
示例 3:

输入:nums = [1,-5,-20,4,-1,3,-6,-3], k = 2
输出:0

提示:

1 <= nums.length, k <= 1e5
-104 <= nums[i] <= 1e4

单调队列+DP :

class Solution {
public:
    int maxResult(vector<int> &nums, int k) {
        deque<int> q = {0};
        for (int i = 1; i < nums.size(); i++) {
            // 1. 出
            if (q.front() < i - k) {
                q.pop_front();
            }
            // 2. 转移
            nums[i] += nums[q.front()];
            // 3. 入
            while (!q.empty() && nums[i] >= nums[q.back()]) {
                q.pop_back();
            }
            q.push_back(i);
        }
        return nums.back();
    }
};

LCP 30. 魔塔游戏

小扣当前位于魔塔游戏第一层,共有 N 个房间,编号为 0 ~ N-1。每个房间的补血道具/怪物对于血量影响记于数组 nums,其中正数表示道具补血数值,即血量增加对应数值;负数表示怪物造成伤害值,即血量减少对应数值;0 表示房间对血量无影响。

小扣初始血量为 1,且无上限。假定小扣原计划按房间编号升序访问所有房间补血/打怪,为保证血量始终为正值,小扣需对房间访问顺序进行调整,每次仅能将一个怪物房间(负数的房间)调整至访问顺序末尾。请返回小扣最少需要调整几次,才能顺利访问所有房间。若调整顺序也无法访问完全部房间,请返回 -1。

示例 1:

输入:nums = [100,100,100,-250,-60,-140,-50,-50,100,150]

输出:1

解释:初始血量为 1。至少需要将 nums[3] 调整至访问顺序末尾以满足要求。

示例 2:

输入:nums = [-200,-300,400,0]

输出:-1

解释:调整访问顺序也无法完成全部房间的访问。

提示:

1 <= nums.length <= 10^5
-10^5 <= nums[i] <= 10^5

参考了题解,贪心+优先队列:

class Solution {
public:
    int magicTower(vector<int>& nums) {
        int numsSize = nums.size();

        long long sum = 0;
        for (int i = 0; i < numsSize; i++) {
            sum += nums[i];
        }

        if (sum < 0)
            return -1;
        int cnt = 0;
        long long hp = 1;
        priority_queue<int, vector<int>, greater<int>> que;
        for (int i = 0; i < numsSize; i++) {
            que.emplace(nums[i]);

            while (hp + nums[i] <= 0) {
                cnt++;
                hp -= que.top();
                que.pop();
            }

            hp += nums[i];
        }
        return cnt;
    }
};

2641. 二叉树的堂兄弟节点 II

给你一棵二叉树的根 root ,请你将每个节点的值替换成该节点的所有 堂兄弟节点值的和 。

如果两个节点在树中有相同的深度且它们的父节点不同,那么它们互为 堂兄弟 。

请你返回修改值之后,树的根 root 。

注意,一个节点的深度指的是从树根节点到这个节点经过的边数。

示例 1:

在这里插入图片描述

输入:root = [5,4,9,1,10,null,7]
输出:[0,0,0,7,7,null,11]
解释:上图展示了初始的二叉树和修改每个节点的值之后的二叉树。

  • 值为 5 的节点没有堂兄弟,所以值修改为 0 。
  • 值为 4 的节点没有堂兄弟,所以值修改为 0 。
  • 值为 9 的节点没有堂兄弟,所以值修改为 0 。
  • 值为 1 的节点有一个堂兄弟,值为 7 ,所以值修改为 7 。
  • 值为 10 的节点有一个堂兄弟,值为 7 ,所以值修改为 7 。
  • 值为 7 的节点有两个堂兄弟,值分别为 1 和 10 ,所以值修改为 11 。

示例 2:
在这里插入图片描述

输入:root = [3,1,2]
输出:[0,0,0]
解释:上图展示了初始的二叉树和修改每个节点的值之后的二叉树。

  • 值为 3 的节点没有堂兄弟,所以值修改为 0 。
  • 值为 1 的节点没有堂兄弟,所以值修改为 0 。
  • 值为 2 的节点没有堂兄弟,所以值修改为 0 。

提示:

树中节点数目的范围是 [1, 1e5] 。
1 <= Node.val <= 1e4

菜鸡不会这题,读者可以看看灵神题解:

class Solution {
public:
    TreeNode *replaceValueInTree(TreeNode *root) {
        root->val = 0;
        vector<TreeNode*> q = {root};
        while (!q.empty()) {
            vector<TreeNode*> nxt;
            // 计算下一层的节点值之和
            int next_level_sum = 0;
            for (auto node : q) {
                if (node->left) {
                    nxt.push_back(node->left);
                    next_level_sum += node->left->val;
                }
                if (node->right) {
                    nxt.push_back(node->right);
                    next_level_sum += node->right->val;
                }
            }

            // 再次遍历,更新下一层的节点值
            for (auto node : q) {
                int children_sum = (node->left ? node->left->val : 0) +
                                   (node->right ? node->right->val : 0);
                if (node->left) node->left->val = next_level_sum - children_sum;
                if (node->right) node->right->val = next_level_sum - children_sum;
            }
            q = move(nxt);
        }
        return root;
    }
};

题解:BFS+算两次

993. 二叉树的堂兄弟节点

在二叉树中,根节点位于深度 0 处,每个深度为 k 的节点的子节点位于深度 k+1 处。

如果二叉树的两个节点深度相同,但 父节点不同 ,则它们是一对堂兄弟节点。

我们给出了具有唯一值的二叉树的根节点 root ,以及树中两个不同节点的值 x 和 y 。

只有与值 x 和 y 对应的节点是堂兄弟节点时,才返回 true 。否则,返回 false。

示例 1:
在这里插入图片描述

输入:root = [1,2,3,4], x = 4, y = 3
输出:false

示例 2:
在这里插入图片描述

输入:root = [1,2,3,null,4,null,5], x = 5, y = 4
输出:true

示例 3:
在这里插入图片描述

输入:root = [1,2,3,null,4], x = 2, y = 3
输出:false

提示:

二叉树的节点数介于 2 到 100 之间。
每个节点的值都是唯一的、范围为 1 到 100 的整数。

深度优先搜索DFS:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left),
 * right(right) {}
 * };
 */
class Solution {
public:
    bool isCousins(TreeNode* root, int x, int y) {
        bool ans = false;
        int depth = 0;
        TreeNode* father = nullptr;
        function<bool(TreeNode*, TreeNode*, int)> dfs =
            [&](TreeNode* node, TreeNode* fa, int d) -> bool {
            if (node == nullptr) {
                return false;
            }
            if (node->val == x || node->val == y) {
                if (depth) {
                    ans = depth == d && father != fa;
                    return true;
                }
                depth = d;
                father = fa;
            }
            return dfs(node->left, node, d + 1) ||
                   dfs(node->right, node, d + 1);
        };
        dfs(root, nullptr, 1);
        return ans;
    }
};

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

给定一个二叉树, 找到该树中两个指定节点的最近公共祖先。

百度百科中最近公共祖先的定义为:“对于有根树 T 的两个节点 p、q,最近公共祖先表示为一个节点 x,满足 x 是 p、q 的祖先且 x 的深度尽可能大(一个节点也可以是它自己的祖先)。”

示例 1:
在这里插入图片描述

输入:root = [3,5,1,6,2,0,8,null,null,7,4], p = 5, q = 1
输出:3
解释:节点 5 和节点 1 的最近公共祖先是节点 3 。

示例 2:

在这里插入图片描述

输入:root = [3,5,1,6,2,0,8,null,null,7,4], p = 5, q = 4
输出:5
解释:节点 5 和节点 4 的最近公共祖先是节点 5 。因为根据定义最近公共祖先节点可以为节点本身。

示例 3:

输入:root = [1,2], p = 1, q = 2
输出:1

提示:

树中节点数目在范围 [2, 1e5] 内。
-1e9 <= Node.val <= 1e9
所有 Node.val 互不相同 。
p != q
p 和 q 均存在于给定的二叉树中。

参考了题解,递归:

/**
 * 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:
    TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
        if (root == nullptr || root == p || root == q) {
            return root;
        }
        auto left = lowestCommonAncestor(root->left, p, q);
        auto right = lowestCommonAncestor(root->right, p, q);
        if (left && right) {
            return root;
        }
        return left ? left : right;
    }
};

94. 二叉树的中序遍历

给定一个二叉树的根节点 root ,返回 它的 中序 遍历 。

示例 1:

在这里插入图片描述

输入:root = [1,null,2,3]
输出:[1,3,2]
示例 2:

输入:root = []
输出:[]
示例 3:

输入:root = [1]
输出:[1]

提示:

树中节点数目在范围 [0, 100] 内
-100 <= Node.val <= 100

进阶: 递归算法很简单,你可以通过迭代算法完成吗?

数据结构基础:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left),
 * right(right) {}
 * };
 */
class Solution {
    void midorder(TreeNode* cur, vector<int>& vec) {
        if (cur == NULL) {
            return;
        }
        midorder(cur->left, vec);
        vec.push_back(cur->val);
        midorder(cur->right, vec);
    }

public:
    vector<int> inorderTraversal(TreeNode* root) {
        vector<int> vec;
        midorder(root, vec);
        return vec;
    }
};

144. 二叉树的前序遍历

给你二叉树的根节点 root ,返回它节点值的 前序 遍历。

示例 1:
在这里插入图片描述

输入:root = [1,null,2,3]
输出:[1,2,3]
示例 2:
在这里插入图片描述

输入:root = []
输出:[]
示例 3:

输入:root = [1]
输出:[1]
示例 4:

输入:root = [1,2]
输出:[1,2]
示例 5:

输入:root = [1,null,2]
输出:[1,2]

提示:

树中节点数目在范围 [0, 100] 内
-100 <= Node.val <= 100

进阶:递归算法很简单,你可以通过迭代算法完成吗?

过年福利,数据结构基础:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left),
 * right(right) {}
 * };
 */
class Solution {
public:
    void preorder(TreeNode* root, vector<int>& vec) {
        if (root == NULL) {
            return;
        }
        vec.push_back(root->val);
        preorder(root->left, vec);
        preorder(root->right, vec);
    }
    vector<int> preorderTraversal(TreeNode* root) {
        vector<int> vec;
        preorder(root, vec);
        return vec;
    }
};

145. 二叉树的后序遍历

给你一棵二叉树的根节点 root ,返回其节点值的 后序遍历 。

示例 1:
在这里插入图片描述

输入:root = [1,null,2,3]
输出:[3,2,1]
示例 2:

输入:root = []
输出:[]
示例 3:

输入:root = [1]
输出:[1]

提示:

树中节点的数目在范围 [0, 100] 内
-100 <= Node.val <= 100

进阶:递归算法很简单,你可以通过迭代算法完成吗?

仍然是数据结构基础:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
 * };
 */
class Solution {
public:
    void lastorder(TreeNode *cur,vector<int> &vec){
        if(cur==NULL){
            return;
        }
        
        lastorder(cur->left,vec);
        lastorder(cur->right,vec);
        vec.push_back(cur->val);
        

    }
    vector<int> postorderTraversal(TreeNode* root) {
        vector<int> vec;
        lastorder(root,vec);
        return vec;
    }
};

987. 二叉树的垂序遍历

给你二叉树的根结点 root ,请你设计算法计算二叉树的 垂序遍历 序列。

对位于 (row, col) 的每个结点而言,其左右子结点分别位于 (row + 1, col - 1) 和 (row + 1, col + 1) 。树的根结点位于 (0, 0) 。

二叉树的 垂序遍历 从最左边的列开始直到最右边的列结束,按列索引每一列上的所有结点,形成一个按出现位置从上到下排序的有序列表。如果同行同列上有多个结点,则按结点的值从小到大进行排序。

返回二叉树的 垂序遍历 序列。

示例 1:

在这里插入图片描述

输入:root = [3,9,20,null,null,15,7]
输出:[[9],[3,15],[20],[7]]
解释:
列 -1 :只有结点 9 在此列中。
列 0 :只有结点 3 和 15 在此列中,按从上到下顺序。
列 1 :只有结点 20 在此列中。
列 2 :只有结点 7 在此列中。
示例 2:
在这里插入图片描述

输入:root = [1,2,3,4,5,6,7]
输出:[[4],[2],[1,5,6],[3],[7]]
解释:
列 -2 :只有结点 4 在此列中。
列 -1 :只有结点 2 在此列中。
列 0 :结点 1 、5 和 6 都在此列中。
1 在上面,所以它出现在前面。
5 和 6 位置都是 (2, 0) ,所以按值从小到大排序,5 在 6 的前面。
列 1 :只有结点 3 在此列中。
列 2 :只有结点 7 在此列中。
示例 3:

在这里插入图片描述

输入:root = [1,2,3,4,6,5,7]
输出:[[4],[2],[1,5,6],[3],[7]]
解释:
这个示例实际上与示例 2 完全相同,只是结点 5 和 6 在树中的位置发生了交换。
因为 5 和 6 的位置仍然相同,所以答案保持不变,仍然按值从小到大排序。

提示:

树中结点数目总数在范围 [1, 1000] 内
0 <= Node.val <= 1000

菜鸡不会orz 看了大佬们的题解(DFS+哈希):

class Solution {
    map<int, vector<pair<int, int>>> groups;

    void dfs(TreeNode* node, int row, int col) {
        if (node == nullptr) {
            return;
        }

        groups[col].emplace_back(row, node->val);
        dfs(node->left, row + 1, col - 1);
        dfs(node->right, row + 1, col + 1);
    }

public:
    vector<vector<int>> verticalTraversal(TreeNode* root) {
        dfs(root, 0, 0);
        vector<vector<int>> ans;
        for (auto& [_, g] : groups) {
            ranges::sort(g);
            vector<int> vals;
            for (auto& [_, val] : g) {
                vals.push_back(val);
            }
            ans.push_back(vals);
        }
        return ans;
    }
};


102. 二叉树的层序遍历

给你二叉树的根节点 root ,返回其节点值的 层序遍历 。 (即逐层地,从左到右访问所有节点)。

示例 1:

在这里插入图片描述

输入:root = [3,9,20,null,null,15,7]
输出:[[3],[9,20],[15,7]]
示例 2:

输入:root = [1]
输出:[[1]]
示例 3:

输入:root = []
输出:[]

提示:

树中节点数目在范围 [0, 2000] 内
-1000 <= Node.val <= 1000
BFS+队列:

/**
* Definition for a binary tree node.
* struct TreeNode {
*     int val;
*     TreeNode *left;
*     TreeNode *right;
*     TreeNode() : val(0), left(nullptr), right(nullptr) {}
*     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
*     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left),
* right(right) {}
* };
*/
class Solution {
public:
   vector<vector<int>> levelOrder(TreeNode* root) {
       queue<TreeNode*> que;
       vector<vector<int>> result;

       if (root != NULL)
           que.push(root);
       while (!que.empty()) {
           int size = que.size();
           vector<int> vec;

           for (int i = 0; i < size; i++) {
               TreeNode* node = que.front();
               que.pop();
               vec.push_back(node->val);
               if (node->left)
                   que.push(node->left);
               if (node->right)
                   que.push(node->right);
           }
           result.push_back(vec);
       }
       return result;
   }
};

107. 二叉树的层序遍历 II

给你二叉树的根节点 root ,返回其节点值 自底向上的层序遍历 。 (即按从叶子节点所在层到根节点所在的层,逐层从左向右遍历)

示例 1:
在这里插入图片描述

输入:root = [3,9,20,null,null,15,7]
输出:[[15,7],[9,20],[3]]
示例 2:

输入:root = [1]
输出:[[1]]
示例 3:

输入:root = []
输出:[]

提示:

树中节点数目在范围 [0, 2000] 内
-1000 <= Node.val <= 1000

对比上一道题,只需反转最后的result:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left),
 * right(right) {}
 * };
 */
class Solution {
public:
    vector<vector<int>> levelOrderBottom(TreeNode* root) {
        queue<TreeNode*> que;
        vector<vector<int>> result;

        if (root != NULL)
            que.push(root);
        while (!que.empty()) {
            int size = que.size();
            vector<int> vec;

            for (int i = 0; i < size; i++) {
                TreeNode* node = que.front();
                que.pop();
                vec.push_back(node->val);
                if (node->left)
                    que.push(node->left);
                if (node->right)
                    que.push(node->right);
            }
            result.push_back(vec);
           
        } 
        reverse(result.begin(), result.end());
        return result;
    }
};

  • 23
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

XforeverZ

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值