牛客ACM-[USACO 2011 Nov G]Above the Median

[USACO 2011 Nov G]Above the Median

题目描述

Farmer John has lined up his N (1 <= N <= 100,000) cows in a row to measure their heights; cow i has height Hi(1<=Hi<=1,000,000,000)H_i (1 <= H_i <= 1,000,000,000)Hi​(1<=Hi​<=1,000,000,000) nanometers–FJ believes in precise measurements! He wants to take a picture of some contiguous subsequence of the cows to submit to a bovine photography contest at the county fair.
The fair has a very strange rule about all submitted photos: a photograph is only valid to submit if it depicts a group of cows whose median height is at least a certain threshold X (1 <= X <= 1,000,000,000).
For purposes of this problem, we define the median of an array A[0…K] to be A[ceiling(K/2)] after A is sorted, where ceiling(K/2) gives K/2 rounded up to the nearest integer (or K/2 itself, it K/2 is an integer to begin with). For example the median of 7,3,2,6 is 6, and the median of 5,4,8 is 5.
Please help FJ count the number of different contiguous subsequences of his cows that he could potentially submit to the photography contest.
给出一串数字,问中位数大于等于X的连续子串有几个。(这里如果有偶数个数,定义为偏大的那一个而非中间取平均)

输入描述

* Line 1: Two space-separated integers: N and X.
* Lines 2…N+1: Line i+1 contains the single integer HiH_iHi​.

输出描述

* Line 1: The number of subsequences of FJ’s cows that have median at least X. Note this may not fit into a 32-bit integer.

示例1

输入

4 6
10
5
6
2

输出

7

说明

FJ’s four cows have heights 10, 5, 6, 2. We want to know how many
contiguous subsequences have median at least 6.
There are 10 possible contiguous subsequences to consider. Of these, only 7
have median at least 6. They are {10}, {6}, {10, 5}, {5, 6}, {6, 2}, {10, 5, 6}, {10, 5, 6, 2}.

解题思路

把大于等于 x 的置为 1 ,小于 x 的置为 −1 ,计算一波前缀和
问题就转化成要找满足 sum[r]−sum[l−1]>=0(l,r) 的对数
枚举这个 l−1 ,即枚举 0n−1 ,每次求 sum[r]>=sum[l−1]r 的个数( 逆序对 )
显然可以用树状数组很方便地维护出来

代码

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=1e6+7;

int n,m;
int a[N],b[N],s[N],c[N],tong[N];
ll ans;

int lowbit(int x){
    return (x)&(-x);
}
int change(int x){
    return x+100001;
}
void add(int x,int v){
    while(x<=N){
        c[x]+=v;
        x+=lowbit(x);
    }
}
inline int query(int x){
    int ret=0;
    while(x>0){
        ret+=c[x];
        x-=lowbit(x);
    }
    return ret;
}
signed main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++){
        cin>>a[i];
        if(a[i]>=m) b[i]=1;
        else b[i]=-1;
    }
    add(change(0),1);
    tong[change(0)]++;
    for(int i=1;i<=n;i++){
        s[i]=s[i-1]+b[i];
        add(change(s[i]),1);
        tong[change(s[i])]++;
    }
    for(int i=0;i<n;i++){
        int t=n-i-query(change(s[i]))+tong[change(s[i])];
        ans+=t;
        add(change(s[i]),-1);
        tong[change(s[i])]--;
    }
    cout<<ans<<endl;
    return 0;
}

总结

水题

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

花崽oyf

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值