AtCoder - 2581 Meaningful Mean

Problem Statement

You are given an integer sequence of length Na= {a1,a2,…,aN}, and an integer K.

a has N(N+1)⁄2 non-empty contiguous subsequences, {al,al+1,…,ar(1≤lrN). Among them, how many have an arithmetic mean that is greater than or equal to K?

Constraints

  • All input values are integers.
  • 1≤N≤2×105
  • 1≤K≤109
  • 1≤ai≤109

Input

Input is given from Standard Input in the following format:

N K
a1
a2
:
aN

Output

Print the number of the non-empty contiguous subsequences with an arithmetic mean that is greater than or equal to K.

Sample Input 1

3 6
7
5
7

Sample Output 1

5

All the non-empty contiguous subsequences of a are listed below:

  • {a1} = {7}
  • {a1,a2} = {7,5}
  • {a1,a2,a3} = {7,5,7}
  • {a2} = {5}
  • {a2,a3} = {5,7}
  • {a3} = {7}

Their means are 7619⁄356 and 7, respectively, and five among them are 6or greater. Note that {a1} and {a3} are indistinguishable by the values of their elements, but we count them individually.

Sample Input 2

1 2
1

Sample Output 2

0

Sample Input 3

7 26
10
20
30
40
30
20
10

Sample Output 3

13


树状数组sb题。

#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int maxn=200005;
ll num[maxn],a[maxn],ans;
int n,r[maxn],f[maxn],k,ky;
inline int read(){
	int x=0; char ch=getchar();
	for(;!isdigit(ch);ch=getchar());
	for(;isdigit(ch);ch=getchar()) x=x*10+ch-'0';
	return x;
}
inline void update(int x,int y){ for(;x<=ky;x+=x&-x) f[x]+=y;}
inline int query(int x){ int an=0; for(;x;x-=x&-x) an+=f[x]; return an;}
int main(){
	scanf("%d%d",&n,&k);
	for(int i=1;i<=n;i++) a[i]=read()-k;
	for(int i=1;i<=n;i++){
	    a[i]+=a[i-1],num[i]=a[i];
	    if(a[i]>=0) ans++;
	}
	sort(num+1,num+n+1);
	ky=unique(num+1,num+n+1)-num-1;
	for(int i=1;i<=n;i++) r[i]=lower_bound(num+1,num+ky+1,a[i])-num;
	for(int i=1;i<=n;i++) ans+=(ll)query(r[i]),update(r[i],1);
	printf("%lld\n",ans);
	return 0;
}

  

 

转载于:https://www.cnblogs.com/JYYHH/p/8921882.html

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值