17. 二叉搜索树的最小绝对值和众数
📃 题目一描述
题目链接:二叉搜索树的最小绝对值
🔔 解题思路
解法一:安装顺序遍历相邻作差,每一次保留上一个遍历的值,和当前遍历的值进行相减;
class Solution {
public:
int res = INT_MAX;
int num = INT_MIN;
int getMinimumDifference(TreeNode* root) {
getNum(root);
return res;
}
void getNum(TreeNode* root) {
if (root == nullptr) return;
getNum(root->left);
if (num != INT_MIN) {
res = min(root->val - num, res);
}
num = root->val;
getNum(root->right);
}
};
解法一换种版本:采用指针记录前面的值
class Solution {
private:
int res = INT_MAX;
TreeNode* pre;
public:
void searchBST(TreeNode* cur) {
if (cur == nullptr) return;
searchBST(cur->left);
// 中序
if (pre != nullptr) {
res = min(res, cur->val - pre->val);
}
pre = cur;
searchBST(cur->right);
}
int getMinimumDifference(TreeNode* root) {
searchBST(root);
return res;
}
};
解法二:采用迭代法
class Solution {
public:
int minDiffInBST(TreeNode* root) {
int res = INT_MAX;
stack<TreeNode*> st;
TreeNode* pre = nullptr;
TreeNode* cur = root;
while (cur || !st.empty()) {
if (cur != nullptr) {
st.push(cur);
cur = cur->left;
}
else {
cur = st.top(); st.pop();
if (pre != nullptr) {
res = min(res, cur->val - pre->val);
}
pre = cur;
cur = cur->right;
}
}
return res;
}
};
💥 复杂度分析
- 时间复杂度:O(n);
- 空间复杂度:O(n);
📃 题目二描述
题目链接:二叉搜索树中的众数
🔔 解题思路
解法一:二叉树的通用解法,用一个map来记录每个数字出现的次数,map再从大到小排序,拿前面大的值即可
class Solution {
public:
unordered_map<int, int> mp;
void searchBST(TreeNode* root) {
if (root == nullptr) return;
// 中序遍历
searchBST(root->left);
mp[root->val]++;
searchBST(root->right);
}
bool static cmp(pair<int, int> &a, pair<int, int> &b) { //从大到小排序
return a.second > b.second;
}
vector<int> findMode(TreeNode* root) {
searchBST(root);
vector<int> res;
vector<pair<int, int>> vec(mp.begin(), mp.end()); //构建vec
sort(vec.begin(), vec.end(), cmp);
res.push_back(vec[0].first);
for (int i = 1; i < vec.size(); i++) {
if (vec[i].second == vec[0].second) res.push_back(vec[i].first);
else break;
}
return res;
}
};
解法二:利用BST树的特性,中序遍历的过程中,相等的两个数是连续的,所以采用 一个maxCount记录元素最大个数,pre记录前面的指针(即可知道前面的值),count记录当前元素的个数,vector< int > res保存答案;
class Solution {
private:
int maxCount;
int count;
vector<int> res;
TreeNode* pre;
public:
void searchBST(TreeNode* root) {
if (root == nullptr) return;
//中序遍历
searchBST(root->left);
if (pre == nullptr) count = 1; //pre不存在
else if (pre->val == root->val) count++; //pre存在 且 前后相等
else count = 1; //pre存在 但 前后不等
pre = root; // 更新pre节点
if (count == maxCount) res.push_back(root->val);
if (count > maxCount) {
res.clear();
res.push_back(root->val);
maxCount = count;
}
searchBST(root->right);
}
vector<int> findMode(TreeNode* root) {
searchBST(root);
return res;
}
};
解法三:迭代法,思想和上面的递归思想一样,可以锻炼一下二叉树迭代;
class Solution {
public:
vector<int> findMode(TreeNode* root) {
vector<int> res;
stack<TreeNode*> st;
int count = 0, maxCount = 0;
TreeNode* pre = nullptr;
TreeNode* cur = root;
while (cur || !st.empty()) {
if (cur) {
st.push(cur);
cur = cur->left;
}
else {
cur = st.top(); st.pop();
//中序
if (pre == nullptr) count = 1; //pre不存在
else if (pre->val == cur->val) count++; //pre存在 且 前后相等
else count = 1; //pre存在 但 前后不等
pre = cur; // 更新pre节点
if (count == maxCount) res.push_back(cur->val);
if (count > maxCount) {
res.clear();
res.push_back(cur->val);
maxCount = count;
}
cur = cur->right;
}
}
return res;
}
};
💥 复杂度分析
- 时间复杂度:O(n);
- 空间复杂度:O(n);