考场想了 5.5 h,第一部分分死活打不出来,做到崩盘,现在重做,感觉自己就是一个sb,放学在地铁上一眼就会了。哎。

可以把一个要求看作一个长度为 \(m\) 的区间:\([l, l + m - 1]\),可以要求这段条件的充要条件是找到一种循环移位,每个墙恰好可以被那个工人挖。然后问题是用最少的区间覆盖完 \([0, n - 1]\)。

可以设一个 DP:

$f_i $:刷完前 \(i\) 个墙的最小要求次数。

  • 如果 \([i - m + 1, i]\) 可以刷,那么 \(f_i = \min_{i-m\le j <i}(f_j) + 1\)。
  • 否则 \(f_i\) 是正无穷。

这个东西显然是一个滑动窗口最值,用单调队列优化,我们现在的就要求快速判断 \([i - m + 1, i]\) 能不能刷。

设 \(len_{i, j}\) 为第 \(i\) 个墙,第 \(j\) 个人刷,最多可以循环移位向前延伸多少个。

对于一个 \(i\),枚举 \(C_i\) 颜色对应的所有的工人 \(u\),转移 \(len_{i, u} = len_{i - 1, (u - 1) \bmod m} + 1\)。

由于 \(\sum f(k)^2 \le 400000\),所以 \(f(k)\) 是 \(600\) 量级的,时间复杂度是 \(O(n \max(f(k)))\) 是可以过的。

但是空间不够,滚动数组就好了,但是还要保证转移的是 \(i - 1\) 次,所以每次转移赋值 \(g_{i \bmod 2, j} = i\),表示这个循环移位最后的位置是 \(i\)。转移判断上次的是不是 \(i - 1\) 就行了。

单调队列还有一些细节,比如正无穷不能扔进队列之类。

#include <vector>
#include <cstring>
#include <iostream>
using namespace std;
const int N = 100005, M = 50005, INF = 0x3f3f3f3f; int f[N], q[N], g[2][M], len[2][M]; vector<int> d[N]; int minimumInstructions(
int n, int m, int K, std::vector<int> c,
std::vector<int> a, std::vector<std::vector<int> > b) {
memset(f, 0x3f, sizeof f);
memset(g, -1, sizeof g);
for (int i = 0; i < K; i++) d[i].clear();
for (int i = 0; i < m; i++) {
for (int j = 0; j < a[i]; j++) {
d[b[i][j]].push_back(i);
}
}
int hh = 0, tt = -1;
for (int i = 0; i < n; i++) {
bool ok = false;
for (int j = 0; j < d[c[i]].size(); j++) {
int u = d[c[i]][j];
g[i & 1][u] = i, len[i & 1][u] = 1;
if (i && g[(i - 1) & 1][(u + m - 1) % m] == i - 1) len[i & 1][u] += len[(i - 1) & 1][(u + m - 1) % m];
if (len[i & 1][u] >= m) ok = true;
}
if (ok) {
while (hh <= tt && q[hh] < i - m) hh++;
if (i < m) f[i] = 1;
else if (hh <= tt) f[i] = f[q[hh]] + 1;
if (f[i] != INF) {
while (hh <= tt && f[q[tt]] >= f[i]) tt--;
q[++tt] = i;
}
}
}
return f[n - 1] == INF ? -1 : f[n - 1];
}

APIO2020 粉刷墙壁的更多相关文章

  1. Codeforces Round #198 (Div. 2)

    A.The Wall 题意:两个人粉刷墙壁,甲从粉刷标号为x,2x,3x...的小块乙粉刷标号为y,2y,3y...的小块问在某个区间内被重复粉刷的小块的个数. 分析:求出x和y的最小公倍数,然后做一 ...

  2. [SinGuLaRiTy] NOIP互测模拟赛

    [SinGuLaRiTy-1045] Copyright (c) SinGuLaRiTy 2017. All Rights Reserved. 源文件名 输入输出文件 时间限制 内存限制 淘气的cch ...

  3. 【资料总结】html开发小实例

    目 录 第1章 1 HTML的基本标签 1 第2章 25 表格基础 25 第3章 53 表单和框架 53 第4章 77 CSS样式表 77 第5章 104 使用Dreamweaver制作网页 104 ...

  4. as well as

    一.as well 用法: 1.as well常用作状语,作“又:也”解,相当于too或also,常位于句末,无须用逗号与句子分开.如: I am going to London and my sis ...

  5. 【日语】日语单词N3_N4_N5

    日语单词N3_N4_N5 单 词 讲 解 あ行单词 ああ:0[副]那样.那种 例句:ああ言うことはしないほうがいい.那样的事情最好不做. 電車の窓からごみを棄てているああ言うことはしないほうがいい. ...

  6. 日语单词N3_N4_N5

    单 词 讲 解 あ行单词 ああ:0[副]那样.那种 例句:ああ言うことはしないほうがいい.那样的事情最好不做. 電車の窓からごみを棄てているああ言うことはしないほうがいい. 挨拶(あいさつ):① 寒暄 ...

  7. java设计模式3——建造者模式

    java设计模式3--建造者模式 1.建造者模式介绍: 建造者模式属于创建型模式,他提供了一种创建对象得最佳方式 定义: 将一个复杂对象的构建和与它的表示分离,使得同样的构建过程可以创建不同的表示 主 ...

  8. poj1821 Fence(dp,单调队列优化)

    题意: 由k(1 <= K <= 100)个工人组成的团队应油漆围墙,其中包含N(1 <= N <= 16 000)个从左到右从1到N编号的木板.每个工人i(1 <= i ...

  9. [LeetCode] Paint Fence 粉刷篱笆

    There is a fence with n posts, each post can be painted with one of the k colors. You have to paint ...

随机推荐

  1. 主动关闭 time-wait 2msl 处理

    先上传后面整理 /* * This routine is called by the ICMP module when it gets some * sort of error condition. ...

  2. Netlink 内核实现分析 4

    netlink 库函数: http://www.infradead.org/~tgr/libnl/doc/core.html#core_netlink_fundamentals #define NET ...

  3. struts.xml中的配置内容

    一些常量的配置 包标签 拦截器标签(自定义拦截器,拦截器栈)       //对待拦截器栈与拦截器是一样的,只是标签不同而已. global-results标签 action标签:拦截器标签,resu ...

  4. CSS opacity设置不透明度

    1.opacity设置不透明度 opacity会将含有这个属性的子类都变成具有opacity属性,可以改变元素.元素内容.字标签的不透明度.而rgba只会改变设置的那个背景颜色的透明度效果 <! ...

  5. addslashes()

    addslashes() 函数返回在预定义字符之前添加反斜杠的字符串. 作用:防止sql注入

  6. FL Studio中有关减少CPU占用率的一些技巧

    在使用FL Studio20进行音乐制作时经常容易碰到的工程卡顿,声音延迟现象绝大部分是由于电脑CPU超负荷运行而导致的.除了提升电脑本身的性能以外,在FL Studio20中我们也可以运用一些方法来 ...

  7. 唯一key的生成规则,可自己视情况改动

    <?php function getMillisecond() { $time = explode ( " ", microtime ()); $time = $time[1 ...

  8. 25. K 个一组翻转链表

    给你一个链表,每 k 个节点一组进行翻转,请你返回翻转后的链表.k 是一个正整数,它的值小于或等于链表的长度.如果节点总数不是 k 的整数倍,那么请将最后剩余的节点保持原有顺序.示例 :给定这个链表: ...

  9. JSX中写 switch case 进行判断

    场景:根据后端返回的数据进行多条件渲染,三元表达式已不能满足条件. 代码: <span> {(() => { switch (record.generalRuleInfos[0]?. ...

  10. Java基础教程——打印流

    打印流 打印流可以把原本输出到控制台的信息输出到文件中.PrintStream是字节打印流(还有个对应的字符打印流是PrintWriter,这里不涉及) System类中有个变量: public fi ...