感觉很是妙啊……这题数次误入歧途...最开始想的二维dp,单调队列优化;无果,卒。于是没忍住看了下标签:暴力枚举?搜索?于是开始想记忆化搜索。以为会有什么很强的剪枝之类的;30分,卒。最后终于回到正道上:50 0000的数据,只可能有O(n) & O(nlogn)两种复杂度吧?在这样的思想+标签线段树的指引下,总算是走向了光明。

暴力,正解的开端。首先考虑最开始的二维dp,转移方程为:dp[i] = min(dp[k] + 1) (k ∈ 1 ~ i - 1) , 且 i ~ k + 1为合法区间。大部分的时间消耗都在于枚举找最值+判断是否合法上。对于这部分的优化,我们先考虑一段合法的区间:要么相差 <= m, 要么都是一个人的粉丝。第二种情况明显特判就行,可以做到O(n), 暂时撇去不谈。再看第一种情况并列出式子:1. abs (a[i] - a[j - 1] - b[i] + b[j - 1]) <= m; 2. a[i] - b[i] - m <= a[j - 1] - b[j - 1] <= a[i] - b[i] + m. 到这里发现,可以用线段树维护区间的最值,将线段树建成 a[i] - b[i]的权值线段树,每次查询在满足条件的范围内的dp最小值就好了。注意要防止爆负数,加上一个大一点的数。

#include <bits/stdc++.h>
using namespace std;
#define INF 1061109567
#define maxn 600000
#define ADD 10000
int n, m, a[maxn], c[maxn], cont = INF, b[maxn], dp[maxn], ans = INF;
int N = ; struct tree
{
int l, r, num;
}T[maxn * ]; int read()
{
int x = ;
char c;
c = getchar();
while(c < '' || c > '') c = getchar();
while(c >= '' && c <= '') x = x * + c - '', c = getchar();
return x;
} void Build(int p, int l, int r)
{
T[p].l = l, T[p].r = r, T[p].num = INF;
if(l == r) return;
int mid = (l + r) >> ;
Build(p << , l, mid), Build(p << | , mid + , r);
} void Getmin(int &x, int y)
{
if(x > y) x = y;
} void update(int p, int x, int num)
{
if(T[p].l == T[p].r)
{
Getmin(T[p].num, num);
return;
}
int mid = (T[p].l + T[p].r) >> ;
if(x <= mid) update(p << , x, num);
else update(p << | , x, num);
T[p].num = min(T[p << ].num, T[p << | ].num);
} int query(int p, int l, int r)
{
int L = T[p].l, R = T[p].r;
if(R < l || L > r) return INF;
if(l <= L && r >= R) return T[p].num;
return min(query(p << , l, r), query(p << | , l, r));
} int main()
{
n = read(), m = read();
memset(dp, 0x3f3f3f, sizeof(dp));
Build(, , N);
for(int i = ; i <= n; i ++)
{
c[i] = read();
a[i] = a[i - ] + (c[i] == );
b[i] = b[i - ] + (c[i] == );
}
dp[] = ;
update(, ADD, dp[]);
for(int i = ; i <= n; i ++)
{
bool flag = false;
if(c[i] == c[i - ]) dp[i] = cont + ;
else flag = true;
Getmin(dp[i], dp[i - ] + );
int tem = query(, a[i] - b[i] - m + ADD, a[i] - b[i] + m + ADD);
Getmin(dp[i], tem + );
if(flag) cont = min(dp[i - ], dp[i]);
else Getmin(cont, dp[i]);
update(, a[i] - b[i] + ADD, dp[i]);
}
printf("%d\n", dp[n]);
return ;
}

【题解】洛谷P2418 yyy loves OI IV的更多相关文章

  1. P2418 yyy loves OI IV

    题目背景 某校2015届有两位OI神牛,yyy和c01. 题目描述 全校除他们以外的N名学生,每人都会膜拜他们中的某一个人.现在老师要给他们分宿舍了.但是,问题来了: 同一间宿舍里的人要么膜拜同一位大 ...

  2. 洛谷 P1580 yyy loves Easter_Egg I

    洛谷 P1580 yyy loves Easter_Egg I 题解: 队列+字符串 #include <cstdio> #include <string> #include ...

  3. [洛谷1580]yyy loves Easter_Egg I

    题目背景 Soha的出题效率着实让人大吃一惊.OI,数学,化学的题目都出好了,物理的题还没有一道.于是,Huntfire,absi2011,lanlan对soha进行轮番炸,准备炸到soha出来,不料 ...

  4. [洛谷2397]yyy loves Maths VI

    题目背景 自动上次redbag用加法好好的刁难过了yyy同学以后,yyy十分愤怒.他还击给了redbag一题,但是这题他惊讶的发现自己居然也不会,所以只好找你 题目描述 他让redbag找众数他还特意 ...

  5. 洛谷P2397 yyy loves Maths VI (mode)

    P2397 yyy loves Maths VI (mode) 题目背景 自动上次redbag用加法好好的刁难过了yyy同学以后,yyy十分愤怒.他还击给了redbag一题,但是这题他惊讶的发现自己居 ...

  6. [CF327E]Axis Walking([洛谷P2396]yyy loves Maths VII)

    题目大意:给一个长度为$n(1\leqslant n\leqslant24)$的序列$S$和$k(0\leqslant k\leqslant2)$个数. 求有多少种$S$的排列方式使得其任何一个前缀和 ...

  7. 洛谷P2396 yyy loves Maths VII

    P2396 yyy loves Maths VII 题目背景 yyy对某些数字有着情有独钟的喜爱,他叫他们为幸运数字;然而他作死太多,所以把自己讨厌的数字成为"厄运数字" 题目描述 ...

  8. 洛谷——P2393 yyy loves Maths II

    P2393 yyy loves Maths II 题目背景 上次蒟蒻redbag可把yyy气坏了,yyy说他只是小学生,蒟蒻redbag这次不坑他了. 题目描述 redbag给了yyy很多个数,要yy ...

  9. 洛谷 P2393 yyy loves Maths II

    P2393 yyy loves Maths II 题目背景 上次蒟蒻redbag可把yyy气坏了,yyy说他只是小学生,蒟蒻redbag这次不坑他了. 题目描述 redbag给了yyy很多个数,要yy ...

随机推荐

  1. 【c学习-10】

    #include #include #define SOURCE 0 //递归函数 /* [基本类型 [整型(int,[长整型(long int), [短整型(short int),长度整型(long ...

  2. ECSHOP和SHOPEX快递单号查询国际EMS插件V8.6专版

    发布ECSHOP说明: ECSHOP快递物流单号查询插件特色 本ECSHOP快递物流单号跟踪插件提供国内外近2000家快递物流订单单号查询服务例如申通快递.顺丰快递.圆通快递.EMS快递.汇通快递.宅 ...

  3. web学习第二天

    今天是学习web的第二天,早上用css3做了个会动的小熊,border-radius为圆的半径, .smallxiong {    width: 400px;    height: 400px;    ...

  4. [JSOI2007] 建筑抢修 (贪心 + 优先队列)

    小刚在玩JSOI提供的一个称之为“建筑抢修”的电脑游戏:经过了一场激烈的战斗,T部落消灭了所有z部落的入侵者.但是T部落的基地里已经有N个建筑设施受到了严重的损伤,如果不尽快修复的话,这些建筑设施将会 ...

  5. python2.7练习小例子(十七)

        17):题目:求s=a+aa+aaa+aaaa+aa...a的值,其中a是一个数字.例如2+22+222+2222+22222(此时共有5个数相加),几个数相加由键盘控制.     程序分析: ...

  6. linux安装oracle远程客户端

    文章参考:http://blog.csdn.net/caomiao2006/article/details/11901123 感谢博友分享O(∩_∩)O~ 安装oracle 远程客户端(一般情况下本地 ...

  7. Go中的系统Signal处理

    package main import "fmt" import "os" import "os/signal" import " ...

  8. 【算法】 string 转 int

    [算法] string 转 int 遇到的一道面试题, 当时只写了个思路, 现给出具体实现 ,算是一种比较笨的实现方式 public class StringToInt { /// <summa ...

  9. 【连载】Maven系列(三) 进阶

    相关文章: 1.<用起来超爽的Maven——入门篇> 2.<用起来超爽的Maven——进阶篇> 一.Maven坐标: Maven世界拥有大量需要构建jar文件,我们需要找一个用 ...

  10. Android应用开发中的夜间模式实现(一)

    前言 在应用开发中会经常遇到要求实现夜间模式或者主题切换具体例子如下,我会先讲解第一种方法. 夜间模式 知乎 网易新闻 沪江开心词场 Pocket 主题切换 腾讯QQ 新浪微博 我今天主要是详述第一种 ...