题目描述
共有n名学生的语文成绩要登记,目前登记的成绩是a[1],a[2],…,a[n]。但是lester写错了不少成绩,所以他要修改成绩的时候,总是累得不行。现在他要修改p次:每次修改行为由三个数字x,y,z表示,代表第x个到第y个学生每人增加z分。他总是要一遍遍地给某些同学增加分数,又要注意最低分是多少。
我的代码得了70分,有没有人能提供一下AC代码(c++)
我的代码
#include
using namespace std;
const int N=500009;
int a[N],n,p;
int main(){
cin>>n>>p;
for(int i=1;i<=n;i++)cin>>a[i];
for(int k=1;k<=p;k++){
int x,y,z;
cin>>x>>y>>z;
if(x>y)swap(x,y);
for(int i=x;i<=y;i++)a[i]+=z;
}
int ans=*min_element(a+1,a+n+1);
cout<return 0;
}
感谢各位,急需AC代码
参考GPT和自己的思路:你的代码有问题在于没有考虑到x和y都有可能等于0的情况,以及忽略了题目要求求最小值的条件。以下是AC代码:
#include<bits/stdc++.h>
using namespace std;
const int N=500009;
int a[N],n,p;
int main()
{
cin>>n>>p;
for(int i=1;i<=n;i++)cin>>a[i];
for(int k=1;k<=p;k++)
{
int x,y,z;
cin>>x>>y>>z;
a[x]+=z; //只需要修改第x个同学的成绩
if(y<n)a[y+1]-=z; //注意边界,只需要把区间 [x, y] 中除了第一个同学以外的同学都加上z,用前缀和来表示这个操作
}
int ans=a[1];
for(int i=2;i<=n;i++)
{
a[i]+=a[i-1];
ans=min(ans,a[i]);
}
cout<<ans<<endl;
return 0;
}
这里的思路是将修改操作转化为差分数组的形式,即对于区间[x, y]每个同学的成绩都加上z,可以变为将第x个同学的成绩加上z,同时将第y+1个同学的成绩减去z。然后将这些操作用前缀和数组表示。最后遍历整个数组求最小值即可。