给定一个整数数组nums,返回该数组某个"范围内的和"在 [ lower,upper ] 之间的总数量
Given an integer array nums
, return the number of range sums that lie in [lower, upper]
inclusive.
Range sum S(i, j)
is defined as the sum of the elements in nums
between indices i
and j
(i
≤ j
), inclusive.
Note:
A naive algorithm of O(n2) is trivial. You MUST do better than that.注意:你的算法必须比O(N^2)性能更快
Example:
Given nums = [-2, 5, -1]
, lower = -2
, upper = 2
,
Return 3
.
The three ranges are : [0, 0]
, [2, 2]
, [0, 2]
and their respective sums are: -2, -1, 2
.
Credits:
Special thanks to @dietpepsi for adding this problem and creating all test cases.
Subscribe to see which companies asked this question
1,朴素的模拟思路:
1),令S(i)表示前i个数之和,比如,比如【-2,5,-1】,s(0)=-2,s(1)=3,s(2)=2...先将所有的和计算出来
2),令S(i, j)表示数组中位置i到j的元素之和,S(i, j)=S(j)-S(i)+a(i)
但是这样做time,o(n^2),space,o(n), Time Limit Exceeded
class Solution {
public:
int countRangeSum(vector<int>& nums, int lower, int upper) {
if(nums.size()==0)
return 0;
vector<int> sums(nums.size(),0);
sums[0]=nums[0];
for (int i = 1; i < nums.size(); ++i)
sums[i] = sums[i-1] + nums[i];
int cnt = 0;
for (int i = 0; i < nums.size(); ++i)
for (int j = i; j < nums.size(); ++j)
{
int gapsum=sums[j] - sums[i]+nums[i];
if ( gapsum>= lower && gapsum <= upper)
cnt++;
}
return cnt;
}
};
优化中.......若干时间后....不会!
参考讨论区:对两层for循环进行优化
class Solution {
public:
int countRangeSum(vector<int>& nums, int lower, int upper) {
int size_nums=nums.size();
vector<long> sums(size_nums+1, 0);
for(int i=0; i<size_nums; i++)
sums[i+1]=sums[i]+nums[i];
return help(sums, 0, size_nums+1, lower, upper);
}
int help(vector<long> &sums, int start, int end, int lower, int upper){
/*** end condition ***/
if(end - start <= 1) return 0;
/*** recursive devidely ***/
int mid=(start+end)/2;
int count=help(sums, start, mid, lower, upper) + help(sums, mid, end, lower, upper);
int j=mid, k=mid, t=mid;
vector<long> cache(end-start, 0);
for(int i=start, r=0; i<mid; i++, r++)
{
while(k<end && sums[k]-sums[i] < lower) k++;
while(j<end && sums[j]-sums[i] <= upper) j++;
/*** merge sorting parts ***/
while(t<end && sums[t] < sums[i]) cache[r++]=sums[t++];
cache[r]=sums[i];
count+=j-k;
}
//copy the merge sorted array to the original sums
for(int i=0; i<t-start; i++)
sums[start+i]=cache[i];
return count;
}
};
注:本博文为EbowTang原创,后续可能继续更新本文。如果转载,请务必复制本条信息!
原文地址:http://blog.csdn.net/ebowtang/article/details/50492602
原作者博客:http://blog.csdn.net/ebowtang