
一· 前缀和
1. 题目

2. 分析
1) 暴力求解
其实就是一个模拟过程;一一进行枚举
对应的时间复杂度:q*n
当 q > 1;每一次在进行加和的过程里面 ,其实是没有必要在重复以上 过程,
可以把指定的数据之和进行存放
2)前缀和思想
采用以空间换时间的思想:借助一个数组,存放指定区间数据的元素之和
创建一个数组 dp
dp[i] : 表示 下标从1~ i 这个区间所有元素的和
那么dp[i-1] : 1~ i-1之间所有元素之和
所以 dp[i] = dp[i-1] + nums[i] nums[i] : 表示当前下标 i 对应的元素
3. 算法原理
根据暴力枚举 的思想,当最坏的情况下,没有必要再次重新进行遍历加和,可以借助前面已经相
加的元素
1)原始数组的输入
2)建立一个前缀和的数组,注意大小比原始数组多一个元素。
3)防溢出的处理,
这是每一个元素的数据范围
前缀和数组 vector<long long> dp(n+1)
4) 核心代码:
dp[i] = dp[i -1] + nums[i]
- 细节处理:
第一个元素的下标应该是从1 开始,
4. OJ代码
cpp
#include <iostream>
using namespace std;
#include <vector>
int main()
{
int n ,q;
cin >>n>>q;
// 1.数组处理,注意大小是 n+1
vector<int> v(n+1);//默认初始化为0
for(int i = 1;i < n+1;++i)
{
int x;
cin>>x;
v[i] = x;
}
// 2.前缀和数组
// vector<int> dp(n+1);
// dp[i]表示数组 V里面前i个元素之和,可能数据溢出
vector<long long > dp(n+1);//防溢出
for(int i = 1;i < n+1;i++)
{
dp[i] = dp[i-1] +v[i];
}
while(q--)
{
int l,r;
cin>>l>>r;
cout<<dp[r]-dp[l-1]<<endl;
}
return 0;
}