HDU 2836 (离散化DP+区间优化)
Reference:http://www.cnblogs.com/wuyiqi/archive/2012/03/28/2420916.html
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=2836
题目大意:计算序列有多少种组合,每个组合至少两个数,使得组合中相邻两个数之差不超过H,序列有重复的数。MOD 9901。
解题思路:
朴素O(n^2)
以样例1 3 7 5为例,如果没有重复的数。
设dp[i]前n个数的方案数,初始化为1。
那么for(1...i...N)
$dp[i]=\sum dp[j]+1\quad,where \quad \left |num[i]-num[j] \right|<=H$
+1是为了计算两个点直接连接的情况,如样例:
dp[1]=1 (无连接)
dp[2]=dp[1]+1=2 (1-3连接)
dp[3]=1 (无连接)
dp[4]=dp[2]+dp[3]+1=4(1-3-5, 3-5,7-5)
如果没有+1,那么就没法dp下去,同时,这样每个点多算了1,所以ans=1+2+1+4-4=4
快速求和优化
上面O(n^2)的原因在于, 原始序列的dp区间不是连续的,比如1,3,8,3,5,7 H=2
5的dp区间可以是2,4,需要多扫一轮来找出这些离散的值。
实际上,dp过程中可以不依赖原始序列顺序。将原始序列排序离散化去重后,变成1,3,5,8
这样,新添加一个box的时候,可以二分找其值在新序列中边界L,R,这样,原本的离散dp求和,
被转化成了连续区间求和$\sum sum(R)-sum(L-1)$
原因很简单,5在实际计算时,在3,3,7中都被牵扯到,是一个对称计算。所以排序去重后可以简化为对连续区间的计算。
至于为什么要去重,主要是为了解决重值的重复计算(原题并没有说没有重值)
比如1,3,3,如果不去重,为第二个3单独开个dp状态,那么1-3被算了两次(dp初始值为1)
所以第二个3,无须再开一个dp状态,直接第一个3基础上算就行了。保证ans-n是最后的结果。
代码
#include "cstdio"
#include "algorithm"
#include "cstring"
using namespace std;
#define maxn 100005
#define mod 9901
int num[maxn],Hash[maxn],n,h,s[maxn];
int lowbit(int x) {return x&(-x);}
int sum(int x)
{
int ret=;
while(x>) ret=(ret+s[x])%mod,x-=lowbit(x);
return ret%mod;
}
void update(int x,int d)
{
while(x<=n) s[x]=(s[x]+d)%mod,x+=lowbit(x);
}
int main()
{
//freopen("in.txt","r",stdin);
while(scanf("%d%d",&n,&h)!=EOF)
{
memset(Hash,,sizeof(Hash));
memset(s,,sizeof(s));
for(int i=;i<=n;i++)
{
scanf("%d",&num[i]);
Hash[i]=num[i];
}
sort(Hash+,Hash+n+);
int diff=unique(Hash+,Hash+n+)-Hash-;
int ans=;
for(int i=;i<=n;i++)
{
int idx=lower_bound(Hash+,Hash+diff+,num[i])-Hash;
int L=lower_bound(Hash+,Hash+diff+,num[i]-h)-Hash;
int R=upper_bound(Hash+,Hash+diff+,num[i]+h)-Hash-;
int dp=(sum(R)-sum(L-)+)%mod;
ans+=dp;
update(idx,dp);
}
printf("%d\n",(ans-n)%mod);
}
}
HDU 2836 (离散化DP+区间优化)的更多相关文章
- hdu 4833 离散化+dp ****
先离散化,然后逆着dp,求出每个点能取到的最大利益,然后看有没有钱,有钱就投 想法好复杂 #include <stdio.h> #include <string.h> #inc ...
- HDU 2829 [Lawrence] DP斜率优化
解题思路 首先肯定是考虑如何快速求出一段铁路的价值. \[ \sum_{i=1}^k \sum_{j=1, j\neq i}^kA[i]A[j]=(\sum_{i=1}^kA[i])^2-\sum_{ ...
- HDU 3480 Division DP斜率优化
解题思路 第一步显然是将原数组排序嘛--然后分成一些不相交的子集,这样显然最小.重点是怎么分. 首先,我们写出一个最暴力的\(DP\): 我们令$F[ i ][ j ] $ 为到第\(i\)位,分成\ ...
- HDU.2829.Lawrence(DP 斜率优化)
题目链接 \(Description\) 给定一个\(n\)个数的序列,最多将序列分为\(m+1\)段,每段的价值是这段中所有数两两相乘的和.求最小总价值. \(Solution\) 写到这突然懒得写 ...
- HDU3480_区间DP平行四边形优化
HDU3480_区间DP平行四边形优化 做到现在能一眼看出来是区间DP的问题了 也能够知道dp[i][j]表示前 i 个节点被分为 j 个区间所取得的最优值的情况 cost[i][j]表示从i ...
- HDOJ(HDU).2844 Coins (DP 多重背包+二进制优化)
HDOJ(HDU).2844 Coins (DP 多重背包+二进制优化) 题意分析 先把每种硬币按照二进制拆分好,然后做01背包即可.需要注意的是本题只需要求解可以凑出几种金钱的价格,而不需要输出种数 ...
- HDOJ(HDU).1059 Dividing(DP 多重背包+二进制优化)
HDOJ(HDU).1059 Dividing(DP 多重背包+二进制优化) 题意分析 给出一系列的石头的数量,然后问石头能否被平分成为价值相等的2份.首先可以确定的是如果石头的价值总和为奇数的话,那 ...
- HDU 3507 [Print Article]DP斜率优化
题目大意 给定一个长度为\(n(n \leqslant 500000)\)的数列,将其分割为连续的若干份,使得 $ \sum ((\sum_{i=j}^kC_i) +M) $ 最小.其中\(C_i\) ...
- R - Weak Pair HDU - 5877 离散化+权值线段树+dfs序 区间种类数
R - Weak Pair HDU - 5877 离散化+权值线段树 这个题目的初步想法,首先用dfs序建一颗树,然后判断对于每一个节点进行遍历,判断他的子节点和他相乘是不是小于等于k, 这么暴力的算 ...
随机推荐
- candence 笔记总结
1.解决candece 启动后提示找不到licence文件的错误: candece的安装就不说了,按照破解步骤一步一步来就行了,但是装完后发现每次启动都会报错 "OrCAD Capture ...
- php 注册审核
注册界面 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3 ...
- GMap.Net开发之技巧小结
1.在GMap地图上,如果要让添加的图标(Marker)有个高亮(highlight)的效果,可以在MouseOver到Marker的时候设置Marker外观效果. 如果要让图标有个报警闪烁的效果,可 ...
- Oracle 监听器
Oracle监听器listener是一个重要的数据库服务器组件,在整个Oracle体系结构中,扮演着重要的作用. 监听器Lisener功能 从当前的Oracle版本看,Listener主要负责下面的几 ...
- bootstrap组件 2
bootstrap组件2 <!DOCTYPE html> <html lang="zh-cn"> <head > <meta charse ...
- eclipse项目中关于导入的项目里提示HttpServletRequest 不能引用的解决办法
eclipse项目中关于导入的项目里提示HttpServletRequest 不能引用的解决办法 当使用eclipse导入外部的web工程时,有时会提示HttpServletRequest, Serv ...
- codeforces Round#380 div2
1.字符串替换ogo+go…换成*** 思路:找ogo记录g位置,做初步替换和标记,非目标字母直接输出, 间隔为2的判断是否一个为标记g,一个为非标记做***替换 #include<iostre ...
- POJ 1947 Rebuilding Roads 树形DP
Rebuilding Roads Description The cows have reconstructed Farmer John's farm, with its N barns (1 & ...
- Linux学习笔记(22) Linux启动管理
1. 系统运行级别 运行级别 含义 关机 1 单用户模式,可想象为windows的安全模式,主要用于系统修复 2 不完全的命令行模式,不含NFS服务 完全的命令行模式,就是标准字符界面 4 系统保留 ...
- BNUOJ1067生成函数入门
https://www.bnuoj.com/v3/problem_show.php?pid=1067