タイトルの説明
同じ値の二分探索木(BST)が与えられた場合、BSTですべてのモード(最も頻度の高い要素)を見つけます。
BSTには次の定義があるとします。
- ノードの左側のサブツリーに含まれるノードの値が、現在のノードの値以下である
- ノードの右側のサブツリーに含まれるノードの値が、現在のノードの値以上である
- 左側と右側の両方のサブツリーは、バイナリ検索ツリーです
例:
例如:
给定 BST [1,null,2,2],
1
\
2
/
2
返回[2].
タイトルリンク: https : //leetcode-cn.com/problems/find-mode-in-binary-search-tree/
アイデア
二分探索木には重要な特性があります。二分探索木の中位トラバーサルシーケンスは昇順です。したがって、二分探索木内のノード値の昇順をたどって、昇順に従ってモードを見つけます。過半数を見つける方法:
- シーケンスの最初の要素を結果に入れ、現在の要素の最大出現回数をcurMaxとして記録し、1に初期化して、現在の要素の出現回数を1として記録します。
- 2番目の要素からトラバースを開始します。現在の要素と前の要素が等しい場合は、cnt ++です。
- cnt == curMaxの場合、現在の要素は結果にあると見なされます。
- cnt> curMaxの場合、より多くのオカレンスを持つモードが検出され、結果がクリアされ、現在の要素が結果に追加されます。
- 現在の要素が前の要素と等しくない場合は、cntを1に設定します。
コードは次のとおりです。
/**
* 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:
vector<int> findMode(TreeNode* root) {
if(root==nullptr) return {};
vector<int> v;
inOrder(root, v);
int cnt = 1;
int curMax = 1;
vector<int> ans;
ans.push_back(v[0]);
for(int i=1; i<v.size(); i++){
if(v[i]==v[i-1]){
cnt++;
}else cnt=1;
if(cnt==curMax){
ans.push_back(v[i]);
}else if(cnt>curMax){
curMax = cnt;
ans.clear();
ans.push_back(v[i]);
}
}
return ans;
}
void inOrder(TreeNode* root, vector<int>& v){
if(root==nullptr) return;
inOrder(root->left, v);
v.push_back(root->val);
inOrder(root->right, v);
}
};
- 時間の複雑さ:O(h + n)
hはツリーの深さ、nはノードの数です。 - スペースの複雑さ:O(n)
nはノードの数です。