蓝桥每日一题(前缀和差分)

//795 前缀和

#include<bits/stdc++.h>
using namespace std;
//795 前缀和
const int N=1e5+10;
int n,m;
int a[N];
int main()
{
    cin>>n>>m;
    for(int i=1;i<=n;i++)cin>>a[i],a[i]+=a[i-1];
    for(int i=0;i<m;i++)
    {
        int l,r;
        cin>>l>>r;
        cout<<a[r]-a[l-1]<<endl;
    }
    return 0;

}

//796子矩阵的和 

#include<bits/stdc++.h>
using namespace std;
//796 子矩阵的和
const int N=1e3+10;
int f[N][N];
int m,n,q;
int main()
{
    cin>>n>>m>>q;
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=m;j++)
        {
            cin>>f[i][j];
            f[i][j]+=f[i-1][j]+f[i][j-1]-f[i-1][j-1];
            cout<<i<<" "<<j<<"为"<<f[i][j]<<endl;
        }
    }
    for(int i=0;i<q;i++)
    {
        int x1,x2,y1,y2;
        cin>>x1>>y1>>x2>>y2;
        int t=f[x2][y2]-f[x1-1][y2]-f[x2][y1-1]+f[x1-1][y1-1];
        cout<<t<<endl;
    }
    return 0;
}

//1230 K倍空间 

自己的暴力做法超时了

#include<bits/stdc++.h>
using namespace std;
//1230 K倍空间 
typedef long long LL;
const int N=1e5+10;
int n,k;
LL a[N];
int main()
{
  cin>>n>>k;
  int cnt=0;
  for(int i=1;i<=n;i++)
  {
      cin>>a[i];
      a[i]+=a[i-1];
      if(a[i]%k==0)cnt++;
  }

  for(int i=1;i<=n;i++)
  {
      for(int j=i+1;j<=n;j++)
      {
          if((a[j]-a[i])%k==0)cnt++;
      }
  }
  cout<<cnt<<endl;
}

y解法:

两个数关于k同余,说明两个数构成的区间的数之和可以被k整除。

但是如果第三个数出现了,那么就会各自与前面的所有同余的数配成一对,所以每次先在ans上加上前面所有同余的数,然后再给数组++。

还要注意的是由于从1开始遍历,可能存在某个si可以整除k,而这个左端点就是s0,,所以我们呢要先初始化这个b[0]=1;也就是相当于前面存在一个可以整除k的数0。

#include<bits/stdc++.h>
using namespace std;
//1230 K倍空间  y做法
typedef long long LL;
const int N=1e5+10;
int n,k;
//大数组一定要放到外面
LL b[N];//用来记录已经出现的同一个某余数的个数
LL a[N];
int main()
{
  scanf("%d%d",&n,&k);
  for(int i=1;i<=n;i++)
  {
      scanf("%lld",&a[i]);
      a[i]+=a[i-1];
  }
  LL ans=0;
  b[0]=1;
  for(int i=1;i<=n;i++)
  {
    ans+=b[a[i]%k];
    b[a[i]%k]++;
  }
  printf("%lld",ans);
}

 

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值