RainX_69

Maximum Segment Sum After Removals (IMPORTANT)

Jan 28th, 2023 (edited)
122
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 5.97 KB | Source Code | 0 0
  1. https://leetcode.com/problems/maximum-segment-sum-after-removals/
  2.  
  3. You are given two 0-indexed integer arrays nums and removeQueries, both of length n. For the ith query, the element in nums at the index removeQueries[i] is removed, splitting nums into different segments.
  4. A segment is a contiguous sequence of positive integers in nums. A segment sum is the sum of every element in a segment.
  5. Return an integer array answer, of length n, where answer[i] is the maximum segment sum after applying the ith removal.
  6. Note: The same index will not be removed more than once.
  7.  
  8.  
  9.  
  10. Example 1:
  11.  
  12. Input: nums = [1,2,5,6,1], removeQueries = [0,3,2,4,1]
  13. Output: [14,7,2,2,0]
  14. Explanation: Using 0 to indicate a removed element, the answer is as follows:
  15. Query 1: Remove the 0th element, nums becomes [0,2,5,6,1] and the maximum segment sum is 14 for segment [2,5,6,1].
  16. Query 2: Remove the 3rd element, nums becomes [0,2,5,0,1] and the maximum segment sum is 7 for segment [2,5].
  17. Query 3: Remove the 2nd element, nums becomes [0,2,0,0,1] and the maximum segment sum is 2 for segment [2].
  18. Query 4: Remove the 4th element, nums becomes [0,2,0,0,0] and the maximum segment sum is 2 for segment [2].
  19. Query 5: Remove the 1st element, nums becomes [0,0,0,0,0] and the maximum segment sum is 0, since there are no segments.
  20. Finally, we return [14,7,2,2,0].
  21.  
  22. Example 2:
  23.  
  24. Input: nums = [3,2,11,1], removeQueries = [3,2,1,0]
  25. Output: [16,5,3,0]
  26. Explanation: Using 0 to indicate a removed element, the answer is as follows:
  27. Query 1: Remove the 3rd element, nums becomes [3,2,11,0] and the maximum segment sum is 16 for segment [3,2,11].
  28. Query 2: Remove the 2nd element, nums becomes [3,2,0,0] and the maximum segment sum is 5 for segment [3,2].
  29. Query 3: Remove the 1st element, nums becomes [3,0,0,0] and the maximum segment sum is 3 for segment [3].
  30. Query 4: Remove the 0th element, nums becomes [0,0,0,0] and the maximum segment sum is 0, since there are no segments.
  31. Finally, we return [16,5,3,0].
  32.  
  33.  
  34. Constraints:
  35.  
  36. n == nums.length == removeQueries.length
  37. 1 <= n <= 10^5
  38. 1 <= nums[i] <= 10^9
  39. 0 <= removeQueries[i] < n
  40. All the values of removeQueries are unique.
  41.  
  42. ---------------------------------------------------------------------------------------------------------------------------------------
  43.  
  44. USING MULTISET AND SETS AND SIMULATION
  45.  
  46. class Solution {
  47. private:
  48.     multiset<long long> sums;
  49.     set<pair<int,int>> ranges;
  50.     vector<long long> prefix;
  51.     int n;
  52. public:
  53.     void SLICE_AND_DICE(set<pair<int,int>>::iterator &itr, vector<int> &nums, int index){
  54.         int start=itr->first;
  55.         int end=itr->second;
  56.  
  57.         ranges.erase(itr);
  58.         sums.erase(sums.find(prefix[end]-prefix[start]+nums[start]));
  59.        
  60.         // breaking down {start,end} -> {start,index-1} , {index+1,end}
  61.         if(index-1>=start){
  62.             sums.insert({prefix[index-1]-prefix[start]+nums[start]});
  63.             ranges.insert({start,index-1});                
  64.         }
  65.         if(index+1<=end){
  66.             sums.insert({prefix[end]-prefix[index+1]+nums[index+1]});
  67.             ranges.insert({index+1,end});
  68.         }
  69.     }
  70.    
  71.     vector<long long> maximumSegmentSum(vector<int>& nums, vector<int>& removeQueries) {
  72.         n=nums.size();
  73.         prefix.resize(n);
  74.        
  75.         for(int i=0;i<n;i++){
  76.             prefix[i]=nums[i];
  77.         }
  78.         for(int i=1;i<n;i++){
  79.             prefix[i]+=prefix[i-1];
  80.         }
  81.        
  82.         sums.insert(prefix[n-1]);
  83.         sums.insert(0); // incase the whole sums multiset becomes empty, answer is 0
  84.         ranges.insert({0,n-1});
  85.        
  86.         vector<long long> res;
  87.         for(auto index: removeQueries){
  88.             auto itr=ranges.upper_bound({index,INT_MAX});
  89.             if(itr!=ranges.begin()){
  90.                 itr--;
  91.                 SLICE_AND_DICE(itr,nums,index);
  92.             }
  93.             else if(itr!=ranges.end()){
  94.                 SLICE_AND_DICE(itr,nums,index);
  95.             }
  96.             res.push_back(*sums.rbegin());
  97.         }
  98.         return res;
  99.     }
  100. };  // SIMULATION USING MULTISET AND SETS
  101.  
  102. ---------------------------------------------------------------------------------------------------------------------------------------
  103.  
  104. USING SEGMENT TREE WITH PREFIX SUFFIX SUM
  105.  
  106. struct Module{
  107.     long long prefix;
  108.     long long suffix;
  109.     long long segMX;
  110.     long long sum;    
  111. };
  112.  
  113. class Solution {
  114. private:
  115.     Module tree[4*100000+5];
  116. public:
  117.     Module merger(Module &left, Module &right){
  118.         Module res;
  119.         res.prefix=max(left.prefix,left.sum+right.prefix);
  120.         res.suffix=max(right.suffix,right.sum+left.suffix);
  121.         res.sum=left.sum+right.sum;
  122.         res.segMX=max({right.segMX,left.segMX,left.suffix+right.prefix});
  123.         return res;
  124.     }
  125.    
  126.     void build(vector<int> &nums, int start, int end, int parent){
  127.         if(start==end){
  128.             tree[parent]={nums[start],nums[start],nums[start],nums[start]};
  129.             return;
  130.         }
  131.         int mid=(start+end)/2;
  132.         build(nums,start,mid,2*parent+1);
  133.         build(nums,mid+1,end,2*parent+2);
  134.         tree[parent]=merger(tree[2*parent+1],tree[2*parent+2]);
  135.     }
  136.    
  137.     void update(int start, int end, int parent, int index, long long int val){
  138.         if(start>end){
  139.             return;
  140.         }
  141.         if(start==end){
  142.             tree[parent]={val,val,val,val};
  143.             return;
  144.         }
  145.         int mid=(start+end)/2;
  146.         if(mid>=index){
  147.             update(start,mid,2*parent+1,index,val);
  148.         }
  149.         else{
  150.             update(mid+1,end,2*parent+2,index,val);
  151.         }
  152.         tree[parent]=merger(tree[2*parent+1],tree[2*parent+2]);
  153.     }
  154.    
  155.     vector<long long> maximumSegmentSum(vector<int>& nums, vector<int>& removeQueries) {
  156.         int n=nums.size();
  157.         build(nums,0,n-1,0);
  158.         vector<long long> res;
  159.         for(auto q: removeQueries){
  160.             update(0,n-1,0,q,-1e14/2);
  161.             res.push_back(max(0ll,tree[0].segMX));
  162.         }
  163.         return res;
  164.     }
  165. };
Advertisement
Add Comment
Please, Sign In to add comment