题解 P3608 【[USACO17JAN]Balanced Photo平衡的照片】

题目

一道树状数组的裸题。

值得一提的是题目的翻译貌似有点问题。

如果L[i]和R[i]的数目相差2倍以上的话,第i头奶牛就是不平衡的。(L[i]和R[i]分别代表第i头奶牛左右两边比她高的数量)。如果L[i]和R[i]中较大者比较小者的数量严格多两倍的话,这头奶牛也是不平衡的

题目中这段话的意思其实是\(max(l[i], r[i]) > 2 * min(l[i], r[i])\),不要被误导了。

接下来是正题。

首先看到这道题,不难想到\(O(n^2)\)的暴力做法,即枚举,但是这样显然会超时,需要优化。

我们发现,题目中要求的东西其实就是一个点左边和右边比他大的点的数量,所以我们枚举的时候其实是浪费了很多时间的,因为一个点的信息并非和其他点没有关联,我们想想怎么能够利用这些信息。

对于一个序列中的某个数,只有比他大的数才会产生影响,所以一个很显然的想法是先从大到小排序。

考虑排序以后,当你操作到\(a[i]\)这个数时,比他大的数一共有\(n-i\)个,也就是说只要你求出这个点左边比他大的数的数量,就可以求出右边的数量。那么你在插入这个数时产生的贡献就是把这个数后面的比他小的数的答案+1。

举个例子,现在有序列3 2 5 1

当你插入3时,2和1的答案都会+1

那么其实就是求一个单点修改的前缀和,每次插入一个数就把这个位置的值从0变成1,然后对于某一个位置\(i\),左边比他大的数就只需要查询一个前缀和就行了。

用树状数组维护,代码也很简洁。

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N = 1000005;
struct sCow
{
    int iH, iBh;
}Cow[N];
bool cmp(sCow x, sCow y){return x.iH > y.iH;}
int iSum[N], n;
int lowbit(int x) {return x & -x;}
void Add(int x, int k){for(; x <= n; x += lowbit(x)) iSum[x] += k;}
int Query(int x){int ans = 0;for(; x; x -= lowbit(x)) ans += iSum[x];return ans;}
int main()
{
    scanf("%d", &n);
    for(int i = 1; i <= n; i++) scanf("%d", &Cow[i].iH), Cow[i].iBh = i;
    sort(Cow + 1, Cow + 1 + n, cmp);
    int iAns = 0;
    for(int i = 1; i <= n; i++)
    {
        Add(Cow[i].iBh, 1);
        int l = Query(Cow[i].iBh - 1);
        int r = i - l - 1;
        if(max(l, r) > 2 * min(l, r)) iAns++;
    }
    cout<<iAns;
}

原文地址:https://www.cnblogs.com/lcezych/p/12114133.html

时间: 2024-10-12 04:37:13

题解 P3608 【[USACO17JAN]Balanced Photo平衡的照片】的相关文章

洛谷P3608 [USACO17JAN]Balanced Photo平衡的照片

P3608 [USACO17JAN]Balanced Photo平衡的照片 题目描述 Farmer John is arranging his NN cows in a line to take a photo (1 \leq N \leq 100,0001≤N≤100,000). The height of the iith cow in sequence is h_ih?i??, and the heights of all cows are distinct. As with all ph

[USACO17JAN]Balanced Photo平衡的照片

[TimeGate] https://www.luogu.org/problem/P3608 [解题思路] 单点修改+区间查询,用树状数组来维护f数组即可 [code] 1 #include <cstdio> 2 #include <algorithm> 3 using namespace std; 4 typedef long long LL; 5 struct Node{ 6 LL h; 7 int cnt; 8 }a[100005]; 9 LL ans; 10 LL b[10

bzoj1702[Usaco2007 Mar]Gold Balanced Lineup 平衡的队列*

bzoj1702[Usaco2007 Mar]Gold Balanced Lineup 平衡的队列 题意: N头牛,一共K种特色.每头牛有多种特色.[i,j]段被称为balanced当且仅当K种特色在[i,j]内拥有次数相同.求最大的[i,j]段长度.n≤100000,k≤30. 题解: 得到式子:a[i][l]-a[j][l]=a[i][l-1]-a[j][l-1],l在2..k之间,移项得a[i][l]-a[i][l-1]=a[j][l]-a[j][l-1],l在2..k之间,故可以定义一个

1702: [Usaco2007 Mar]Gold Balanced Lineup 平衡的队列

1702: [Usaco2007 Mar]Gold Balanced Lineup 平衡的队列 Time Limit: 5 Sec  Memory Limit: 64 MBSubmit: 510  Solved: 196[Submit][Status][Discuss] Description Farmer John's N cows (1 <= N <= 100,000) share many similarities. In fact, FJ has been able to narrow

【BZOJ】1702: [Usaco2007 Mar]Gold Balanced Lineup 平衡的队列

[题意]给定n头牛,k个特色,给出每头牛拥有哪些特色的二进制对应数字,[i,j]平衡当且仅当第i~j头牛的所有特色数量都相等,求最长区间长度. [算法]平衡树+数学转化 [题解]统计前缀和sum[i][j]表示前i头牛特色为j的数量,则区间i~j平衡需要满足: sum[j][1]-sum[i-1][1]=sum[j][2]-sum[i-1][2]=sum[j][3]-sum[i-1][3]=... 移项可得,只须 sum[j][1]-sum[j][2]=sum[i-1][1]-sum[i-1][

hdu 3709 Balanced Number(平衡数)--数位dp

Balanced Number Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65535/65535 K (Java/Others)Total Submission(s): 9036    Accepted Submission(s): 4294 Problem Description A balanced number is a non-negative integer that can be balanced if a pi

SPOJ BALNUM Balanced Numbers 平衡数(数位DP,状压)

题意: 平衡树定义为“一个整数的某个数位若是奇数,则该奇数必定出现偶数次:偶数位则必须出现奇数次”,比如 222,数位为偶数2,共出现3次,是奇数次,所以合法.给一个区间[L,R],问有多少个平衡数? 思路: 这题比较好解决,只有前导零问题需要解决.如果枚举到011,那么其前导零(偶数)出现了1次而已,而此数11却是平衡数,所以不允许前导零的出现! 由于dfs时必定会枚举到前导零,否则位数较少的那些统计不到.状态需要3维or2维也行,3维的比较容易处理,用一维表示数位出现次数,另一维表示数位是否

bzoj4759 [Usaco2017 Jan]Balanced Photo

传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=4759 [题解] 排序,从大到小插入,树状数组统计. # include <vector> # include <stdio.h> # include <string.h> # include <iostream> # include <algorithm> // # include <bits/stdc++.h> using n

[Usaco2007 Mar]Gold Balanced Lineup 平衡的队列

Description N(1<=N<=100000)头牛,一共K(1<=K<=30)种特色,每头牛有多种特色,用二进制01表示它的特色ID.比如特色ID为13(1101),则它有第1.3.4种特色.[i,j]段被称为balanced当且仅当K种特色在[i,j]内拥有次数相同.求最大的[i,j]段长度. Input 第一行给出数字N,K 下面N行每行给出一个数字,代表这头牛的特征值 Output 求出一个区间值,在这个区间中,所有牛的这K种特征值的总和是相等的. Sample In