• [USACO]奶牛抗议(DP+树状数组+离散化)


    Description

    约翰家的N头奶牛聚集在一起,排成一列,正在进行一项抗议活动。第i头奶牛的理智度 为Ai,Ai可能是负数。约翰希望奶牛在抗议时保持理性,为此,他打算将所有的奶牛隔离成 若干个小组,每个小组内的奶牛的理智度总和都要大于零。由于奶牛是按直线排列的,所以 一个小组内的奶牛位置必须是连续的。

    请帮助约翰计算一下,存在多少种不同的分组的方案。由于答案可能很大,只要输出答 案除以1,000,000,009的余数即可。

    Solution

    容易想到设(F[i])表示 到第头(i)奶牛的方案数,

    那么就有(F[i]=sum F[j](sum[i]-sum[j] geq 0)), sum为前缀和,

    但如果直接枚举时间大概为(O(n^2)),显然会超时,那么考虑优化

    式子可化为(F[i]=sum F[j](sum[i]geq sum[j])) ,

    可以用前缀和为下标,构造树状数组维护小于等于(sum[i])(F) 的和

    那么前缀和很大,但是中间有很多没用的,离散化即可

    注意(F[0]=1)要提前预处理进树状数组,时间复杂度(O(nlogn))

    Code

    #include <cstdio>
    #include <algorithm>
    #define LL long long
    #define N 1000010
    using namespace std;
    
    struct info {
    	int id;
    	LL sum;
    } a[N];
    const int yh = 1e9 + 9;
    int n, t, p[N];
    LL Ans, f[N];
    
    int lowbit(int x) {
    	return x & (-x);
    }
    
    inline int read() {
    	int x = 0, f = 1; char ch = getchar();
    	while (ch < '0' || ch > '9') {if (ch == '-')f = -1; ch = getchar();}
    	while (ch >= '0' && ch <= '9') {x = x * 10 + ch - '0'; ch = getchar();}
    	return x * f;
    }
    
    bool cmp(info a, info b) {return a.sum < b.sum;}
    
    void add(int x, LL v) {
    	while (x <= n) {
    		f[x] = (f[x] + v) % yh;
    		x += lowbit(x);
    	}
    }
    
    LL cal(int x) {
    	LL r = 0;
    	while (x) {
    		r = (r + f[x]) % yh;
    		x -= lowbit(x);
    	}
    	return r;
    }
    
    int main() {
    	n = read();
    	for (int i = 1; i <= n; ++i) {
    		a[i].sum = a[i - 1].sum + read();
    		a[i].id = i;
    	}
    	a[n + 1].id = n + 1;	//F[0]=1
    	a[n + 1].sum = 0;
    	sort(a + 1, a + n + 2, cmp);
    	for (int i = 1; i <= n + 1; i++) {	//离散化
    		if (i == 1 || a[i].sum != a[i - 1].sum) ++t;
    		p[a[i].id] = t;
    	}
    	add(p[n + 1], 1);
    	for (int i = 1; i <= n; ++i) {
    		Ans = cal(p[i]);
    		add(p[i], Ans);
    	}
    	printf("%lld
    ", Ans);
    	return 0;
    }
    
  • 相关阅读:
    SQL基础复习03--数据查询SQL语句(单表查询)
    SQL基础复习02--数据操纵SQL语句
    数据结构与算法01--复杂度
    SQL基础复习01--SQL基础与数据定义SQL语句
    Azure Data Studio的初步了解与使用
    ASP.NET Core Web API 使用DynamicLinq实现排序功能
    Vue3-说说Vue 3.0中Treeshaking特性?举例说明一下?
    JavaScript高频手写面试题
    Java常用文件操作-1
    Java 架构师之路(2)
  • 原文地址:https://www.cnblogs.com/void-f/p/7736798.html
Copyright © 2020-2023  润新知