剑指offer打卡 week4
46. 二叉搜索树的后序遍历序列
https://www.acwing.com/problem/content/44/
二叉搜索树就是左儿子比根小 右儿子比根大
后续遍历直接获得根节点 然后我们看能不能找到一个分界点 左边的元素都比根节点小 即左儿子 右边的元素都比根节点大 即右儿子 然后递归处理
如果找不到说明无法构建
class Solution {
public:
vector<int>seq;
bool verifySequenceOfBST(vector<int> sequence) {
seq=sequence;
if(sequence.size()==0) return true;
return dfs(0,seq.size()-1);
}
bool dfs(int l,int r){
if(l>=r) return true;
int k=l;
int root=seq[r];
while(k<r && seq[k]<root) k++;
for(int i=k;i<=r;i++){
if(seq[i]<root) return false;
}
return dfs(l,k-1)&&dfs(k,r-1);
}
};
47. 二叉树中和为某一值的路径
https://www.acwing.com/problem/content/45/
class Solution {
public:
vector<vector<int>>ans;
int SUM=0;
vector<vector<int>> findPath(TreeNode* root, int sum) {
vector<int>temp;
if(!root) return ans;
SUM=sum;
temp.push_back(root->val);
dfs(root,temp,root->val);
return ans;
}
void dfs(TreeNode* root,vector<int>&temp,int sum){
if(sum==SUM && (!root->left) && (!root->right)){
ans.push_back(temp);
}
if(root->left && sum+(root->left->val)<=SUM){
temp.push_back(root->left->val);
dfs(root->left,temp,sum+(root->left->val));
temp.pop_back();
}
if(root->right && sum+(root->right->val)<=SUM){
temp.push_back(root->right->val);
dfs(root->right,temp,sum+(root->right->val));
temp.pop_back();
}
}
};
49. 二叉搜索树与双向链表
https://www.acwing.com/problem/content/87/
class Solution {
public:
TreeNode* pre = NULL;
TreeNode* convert(TreeNode* root) {
dfs(root);
while(root && root->left) root = root->left;
return root;
}
void dfs(TreeNode* root){
if(!root) return;
dfs(root->left);
root->left = pre;
if(pre) pre->right = root;
pre = root;
dfs(root->right);
}
};
51. 数字排列
https://www.acwing.com/problem/content/47/
class Solution {
public:
vector<bool> st;
vector<int> path;
vector<vector<int>> ans;
vector<vector<int>> permutation(vector<int>& nums) {
sort(nums.begin(), nums.end());
st = vector<bool>(nums.size(), false);
path = vector<int>(nums.size());
dfs(nums, 0, 0);
return ans;
}
void dfs(vector<int>& nums, int u, int start)
{
if (u == nums.size())
{
ans.push_back(path);
return;
}
for (int i = start; i < nums.size(); i ++ )
if (!st[i])
{
st[i] = true;
path[i] = nums[u];
if (u + 1 < nums.size() && nums[u + 1] != nums[u])
dfs(nums, u + 1, 0);
else
dfs(nums, u + 1, i + 1);
st[i] = false;
}
}
};
52. 数组中出现次数超过一半的数字
https://www.acwing.com/problem/content/description/48/
方法基本就很阴间 很难自己想出来
class Solution {
public:
int moreThanHalfNum_Solution(vector<int>& nums) {
int cnt=1,value=nums[0];
for(int i=1;i<nums.size();i++){
if(value==nums[i]){
cnt++;
}
else {
cnt--;
}
if(cnt==0){
value=nums[i];
cnt++;
}
}
return value;
}
};
53. 最小的k个数
https://www.acwing.com/problem/content/49/
手写个堆当练习。
class Solution {
public:
int heap[1005],cnt,now,next;
vector<int>ans;
void push(int x){
heap[++cnt]=x;
now=cnt;
while(now){
next=(now>>1);
if(heap[next]>heap[now]){
swap(heap[next],heap[now]);
now=next;
}
else break;
}
}
void pop(){
swap(heap[1],heap[cnt]);
cnt--;
now=1;
while((now<<1)<=cnt){
next=(now<<1);
if(next+1<=cnt&&heap[next+1]<heap[next]) next++;//如果右儿子比左儿子更小,则选择右儿子交换
if(heap[now]>heap[next]){
swap(heap[next],heap[now]);
now=next;
}
else break;//已符合要求
}
}
vector<int> getLeastNumbers_Solution(vector<int> input, int k) {
for(auto x:input){
push(x);
}
for(int i=0;i<k;i++){
ans.push_back(heap[1]);
pop();
}
return ans;
}
};
55. 连续子数组的最大和
https://www.acwing.com/problem/content/50/
class Solution {
public:
int maxSubArray(vector<int>& nums) {
int res = INT_MIN;
int s = 0;
for(int x : nums){
if(s<0){
s = 0;
}
s += x;
res = max(res,s);
}
return res;
}
};

浙公网安备 33010602011771号