leetcode周赛 233

A:水题,数据范围较小,直接暴力模拟。

 1 class Solution {
 2 public:
 3     bool check(vector<int> a,int i,int j ){
 4         for(int k=i+1;k<=j;k++){
 5             if(a[k]<=a[k-1]){
 6                 return false;
 7             }
 8         }
 9         return true;
10     }
11     int maxAscendingSum(vector<int>& nums) {
12         int n=nums.size();
13         int res=0;
14         for(int i=0;i<n;i++){
15             for(int j=0;j<n;j++){
16                 int sum=0;
17                 if(check(nums,i,j)){
18                     for(int k=i;k<=j;k++){
19                         sum+=nums[k];
20                     }
21                     res=max(res,sum);
22                 }
23                 
24             }
25         }
26         return res;
27     }
28 };

 

 

B:题目非常长,但是做法还是非常容易想到的, 给定两种订单,买和卖,当买>=卖的时候都可以完成这个和对应的订单。

然后数据范围为1e5,非常明显的堆的题目。

 1 struct Node{
 2     int v,cnt;
 3     bool operator< (const Node& t)const {
 4         return v<t.v;
 5     }
 6     bool operator> (const Node& t)const {
 7         return v>t.v;
 8     }
 9 };
10 class Solution {
11 public:
12     const int mod=1e9+7;
13     int getNumberOfBacklogOrders(vector<vector<int>>& orders) {
14         priority_queue<Node,vector<Node>,less<Node>> q0;
15         priority_queue<Node,vector<Node>,greater<Node>> q1;
16         for(auto x:orders){
17             int v=x[0],cnt=x[1],t=x[2];
18             if(t==0){
19                 if(q1.size()==0){
20                     q0.push({v,cnt});
21                     continue;
22                 }
23                 while(cnt&&q1.size()&&q1.top().v<=v){
24                     auto tmp=q1.top();
25                     q1.pop();
26                     if(tmp.cnt<=cnt){
27                         cnt-=tmp.cnt;
28                     }else{
29                         tmp.cnt-=cnt;
30                         cnt=0;
31                         q1.push(tmp);
32                     }
33                 }
34                 if(cnt){
35                     q0.push({v,cnt});
36                 }
37             }else{
38                 if(q0.size()==0){
39                     q1.push({v,cnt});
40                     continue;
41                 }
42                 while(cnt&&q0.size()&&q0.top().v>=v){
43                     auto tmp=q0.top();
44                     q0.pop();
45                     if(tmp.cnt<=cnt){
46                         cnt-=tmp.cnt;
47                     }else{
48                         tmp.cnt-=cnt;
49                         cnt=0;
50                         q0.push(tmp);
51                     }
52                 }
53                 if(cnt){
54                     q1.push({v,cnt});
55                 }
56             }
57         }
58         long long res=0;
59         while(q0.size()){
60             res+=q0.top().cnt;
61             q0.pop();
62             res%=mod;
63         }
64         while(q1.size()){
65             res+=q1.top().cnt;
66             q1.pop();
67             res%=mod;
68         }
69         return res%mod;
70     }
71 };

 

 

C:给定数据长度和数组和,满足相邻元素差<=1,最大化nums [ index ]的值。

存在两种可能,sum非常的大足以覆盖整个数组

  sum非常的小,只能覆盖一部分数组,其余的元素需要用0补足。

  最开始我就只考虑到了第一种情况,推公式推了半天,然后做错了,浪费了非常多的时间。

nums[i]为正整数,所以首先全部赋值为1,然后从index开始向两边扩散。

 1 class Solution {
 2 public:
 3     int maxValue(int n, int index, int maxSum) {
 4         int l=index,r=index;
 5         int res=1;
 6         int rest=maxSum-n;
 7         while(l>0||r<n-1){
 8             int len=r-l+1;
 9             if(rest>=len){
10                 res++;
11                 rest-=len;
12             }else{
13                 break;
14             }
15             l=max(l-1,0);
16             r=min(r+1,n-1);
17         }
18         res+=rest/n;
19         return res;
20     }
21 };

 

 

D:给定一个数组,一个区间,问这个数组内有多少对异或值在这个区间内。

数据范围为2e4,所以暴力是不行的, 可以使用字典树(题解)。

但是有些题解真的让我抓狂,真就别人看不懂的题解就是好的呗。

cnt整一条路上的cnt都会增加,如此的话就能够统计在这一棵子树共有多少个数了。

如果x某一位为1,high同一位也为1.

那么我们可以直接res+=cnt[son[p][1]],p=son[p][0]

加上在这一位上为1的数,再看这一位上位0的数。

共有四种情况,此处不一一列举了。

 1 const int N=2e4+10;
 2 int son[N*20][2],cnt[N*20],idx;
 3 class Solution {
 4 public:
 5     void insert(int x)
 6     {
 7         int p=0;
 8         for(int i=15;i>=0;--i)
 9         {
10             int u = (x>>i)&1;
11             if(!son[p][u]) son[p][u]=++idx;
12             p=son[p][u];
13             ++cnt[p];
14         }
15     }
16 
17     int query(int x,int hi){
18         int p=0;
19         int res=0;
20         for(int i=15;i>=0;i--){
21             int u=x>>i&1,h=hi>>i&1;
22             if(u==0&&h==0){
23                 p=son[p][0];
24             }
25             if(u==0&&h==1){
26                 res+=cnt[son[p][0]];
27                 p=son[p][1];
28             }
29             if(u==1&&h==0){
30                 p=son[p][1];
31             }
32             if(u==1&&h==1){
33                 res+=cnt[son[p][1]];
34                 p=son[p][0];
35             }
36             if(!p) return res;
37         }
38         return res;
39     }
40     int countPairs(vector<int>& nums, int low, int high) {
41         memset(son,0,sizeof son);
42         memset(cnt,0,sizeof cnt);
43         idx=0;
44         int res=0;
45         for(auto &i:nums)
46         {
47             res+=query(i,high+1)-query(i,low);//根据query,找出的是a^b<hi的b,所以得加1
48             insert(i);
49         } 
50         return res;
51 
52     }
53 };

 

posted on 2021-03-23 20:17  greenofyu  阅读(13)  评论(0编辑  收藏  举报