如果将$x$和$y$都离散,那么删除的点的$x_{i}$和$y_{i}$必然都组成了一个完整的区间(包括过程中)

将所有点按$x$排序,再令$f[i][j][0/1]$表示当删除完区间$[i,j]$且位于点$i$/点$j$时答案(若无法删除记为$\infty$),转移考虑下一次删除的点($i-1$或$j+1$)是否可行

(这里的答案指在这个状态后删除尽量多的点所需最短时间,因此最终答案为$f[i][i][0/1]$,初始状态不易确定,可以记忆化搜索来做,当无法转移即为0)

根据上面的结论,记$mn=\min_{i\le k\le j}y_{k}$、$mx=\max_{i\le k\le j}y_{k}$,假设下一次选了$i-1$,那么即要求$y_{i-1}$等于$mn-1$或$mx+1$(选$j+1$同理),由此判定时间复杂度为$o(n^{2})$

贪心,对于存在区间$[i,j]$满足$\forall i\le k<j,|y'_{k}-y'_{k+1}|=1$,当我们删除了$i$接下来必然删除$i+1,...,j$(删除$j$同理),因此不妨将其缩为1个点(仅是视为一个点),但此时复杂度貌似仍然是$o(n^{2})$的

定义一个区间合法当且仅当其在记忆化搜索过程中会被得到,时间复杂度即为合法区间数

一个更有意义的判定方法,区间$[i,j]$合法当且仅当$mx-mn=j-i$且可以通过不断删除两端的最小值或最大值使其为空(即若$y_{i}=mn或mx$即可删除$i$,$j$同理)

对于删除,我们可以贪心,可以发现删除后一定“更容易”删除,即若一个区间合法,任意合法的删除顺序都可以将其删除

定义$S_{l,r}$表示区间$[l,r]$的子合法区间数,$Sl_{l,r}$表示区间$[l,r]$以$l$为左端点的子合法区间数,$Sr_{l,r}$类似(即以$r$为右端点)

对一个合法区间$[l,r]$,考虑如何转移求$S_{l,r}$,分类讨论:

1.$l$和$r$都可以删除,$S_{l,r}=Sl_{l,r-1}+Sr_{l+1,r}+S_{l-1,r-1}+1$

2.$l$和$r$中只有一个可以删除(假设为$l$),$S_{l,r}=S_{l+1,r}+1$

来考虑第一种情况中$Sl_{l,r-1}$的级别,不妨假设$l$为$[l,r]$区间最小值,则$r$必然为区间最大值,然后对于$a_{l}+1$的位置分类讨论:

1.若$a_{l}+1$位于$r-1$,即$a_{r-1}=a_{l}+1$,那么$Sl_{l,r-1}\le 2$($[l,l]$,$[l,r-1]$)

2.若$a_{l}+1$位于$l+1$,即$a_{l+1}=a_{l}+1$,则一定被缩点了,不存在该情况;

3.否则$a_{l+1}$和$a_{r-1}$必然都不是$[l+1,r-1]$区间最小值,同时若$a_{r-1}$为区间最大值必然满足$a_{r-1}=a_{r}-1$,会被缩点,因此只能$a_{l+1}=a_{r}-1$,那么为了保证$[a_{l},a_{l+1}]$中的数都出现,$Sl_{l,r-1}\le 2$

因此$S_{l,r}$为$o(r-l)$的级别,总合法区间数为$o(n)$级别

另外,由于要记忆化搜索记录,需要map维护,最终时间复杂度为$o(n\log_{2}n)$,可以通过

(还有一个细节,可以通过八个方向走到给定点,但平时只能走到相邻的4个方向,相当于可以减少$r-l$步,这个可以在无法转移时记录)

 1 #include<bits/stdc++.h>
2 using namespace std;
3 #define N 200005
4 #define ll long long
5 struct ji{
6 int x,y,id;
7 }a[N];
8 vector<int>v;
9 map<int,ll>f[2][N];
10 int n,ls[N],rs[N];
11 ll ans[N];
12 bool cmp(ji x,ji y){
13 return x.x<y.x;
14 }
15 int dis(ji x,ji y){
16 return abs(x.x-y.x)+abs(v[x.y]-v[y.y]);
17 }
18 ll dp(int l,int r,int mn,int mx,int p){
19 if (f[p][l][r])return f[p][l][r];
20 f[p][l][r]=1e15;
21 ji o=a[l+p*(r-l)];
22 if ((l>1)&&((a[l-1].y==mn-1)||(a[l-1].y==mx+1))){
23 int k=ls[l-1];
24 f[p][l][r]=min(f[p][l][r],dp(k,r,min(mn,a[k].y),max(mx,a[k].y),0)+dis(o,a[k]));
25 }
26 if ((r<n)&&((a[r+1].y==mn-1)||(a[r+1].y==mx+1))){
27 int k=rs[r+1];
28 f[p][l][r]=min(f[p][l][r],dp(l,k,min(mn,a[k].y),max(mx,a[k].y),1)+dis(o,a[k]));
29 }
30 if (f[p][l][r]==1e15)f[p][l][r]=-(r-l);
31 return f[p][l][r];
32 }
33 int main(){
34 scanf("%d",&n);
35 for(int i=1;i<=n;i++){
36 scanf("%d%d",&a[i].x,&a[i].y);
37 a[i].id=i;
38 v.push_back(a[i].y);
39 }
40 sort(v.begin(),v.end());
41 for(int i=1;i<=n;i++)a[i].y=lower_bound(v.begin(),v.end(),a[i].y)-v.begin();
42 sort(a+1,a+n+1,cmp);
43 ls[1]=1,rs[n]=n;
44 for(int i=2;i<=n;i++)
45 if (abs(a[i-1].y-a[i].y)!=1)ls[i]=i;
46 else ls[i]=ls[i-1];
47 for(int i=n-1;i;i--)
48 if (abs(a[i+1].y-a[i].y)!=1)rs[i]=i;
49 else rs[i]=rs[i+1];
50 for(int i=1;i<=n;i++)ans[a[i].id]=dp(i,i,a[i].y,a[i].y,0);
51 for(int i=1;i<=n;i++)printf("%lld\n",ans[i]);
52 }

[atAGC047F]Rooks的更多相关文章

  1. UVA - 11134 Fabled Rooks[贪心 问题分解]

    UVA - 11134 Fabled Rooks We would like to place n rooks, 1 ≤ n ≤ 5000, on a n × n board subject to t ...

  2. (light OJ 1005) Rooks dp

    http://www.lightoj.com/volume_showproblem.php?problem=1005        PDF (English) Statistics Forum Tim ...

  3. 01_传说中的车(Fabled Rooks UVa 11134 贪心问题)

    问题来源:刘汝佳<算法竞赛入门经典--训练指南> P81: 问题描述:你的任务是在n*n(1<=n<=5000)的棋盘上放n辆车,使得任意两辆车不相互攻击,且第i辆车在一个给定 ...

  4. uva 11134 fabled rooks (贪心)——yhx

    We would like to place n rooks, 1 n 5000, on a n nboard subject to the following restrictions• The i ...

  5. L - Fabled Rooks(中途相遇法和贪心)

    Problem F: Fabled Rooks We would like to place n rooks, 1 ≤ n ≤ 5000, on a n×n board subject to the ...

  6. UVA 11134 - Fabled Rooks(贪心+优先队列)

    We would like to place  n  rooks, 1 ≤  n  ≤ 5000, on a  n×n  board subject to the following restrict ...

  7. 贪心 uvaoj 11134 Fabled Rooks

    Problem F: Fabled Rooks We would like to place n rooks, 1 ≤ n ≤ 5000, on a n×n board subject to the ...

  8. uva 11134 - Fabled Rooks(问题转换+优先队列)

    题目链接:uva 11134 - Fabled Rooks 题目大意:给出n,表示要在n*n的矩阵上放置n个车,并且保证第i辆车在第i个区间上,每个区间给出左上角和右小角的坐标.另要求任意两个车之间不 ...

  9. 1005 - Rooks(规律)

    1005 - Rooks   PDF (English) Statistics Forum Time Limit: 1 second(s) Memory Limit: 32 MB A rook is ...

随机推荐

  1. 学习Tomcat(七)之Spring内嵌Tomcat

    前面的文章中,我们介绍了Tomcat容器的关键组件和类加载器,但是现在的J2EE开发中更多的是使用SpringBoot内嵌的Tomcat容器,而不是单独安装Tomcat应用.那么Spring是怎么和T ...

  2. SimpleDateFormat、Date和String互转

    今天在修改bug时遇到一个查询异常:根据时间段查询的时候,如果查询时间段含12点钟,那么能查到时间段之外的其他数据: 跟踪了数据流动发现,前同事写的程序中,有一处是讲前端传来时间字符串转为Date的一 ...

  3. 轻量级 Java 基础开发框架,Solon & Solon Cloud 1.5.48 发布

    Solon 已有120个生态扩展插件,此次更新主要为细节打磨: 增加 solon.serialization,做为序列化的基础插件 优化 所有Json序列化插件,使之可方便定制类型序列化 public ...

  4. 项目实战:Qt文件改名工具 v1.2.0(支持递归检索,搜索:模糊匹配,前缀匹配,后缀匹配;重命名:模糊替换,前缀追加,后缀追加)

    需求   在整理文件和一些其他头文件的时候,需要对其名称进行整理和修改,此工具很早就应该写了,创业后,非常忙,今天抽空写了一个顺便提供给学习.   工具和源码下载地址   本篇文章的应用包和源码包可在 ...

  5. 【UE4 设计模式】单例模式 Singleton Pattern

    概述 描述 保证一个类只有一个实例 提供一个访问该实例的全局节点,可以视为一个全局变量 仅在首次请求单例对象时对其进行初始化. 套路 将默认构造函数设为私有, 防止其他对象使用单例类的 new运算符. ...

  6. 什么是产品待办列表?(What is Product Backlog)

    正如scrum指南中所描述的,产品待办事项列表是一个紧急而有序的列表,其中列出了改进产品所需的内容.它是scrum团队承担的工作的唯一来源. 在sprint计划 (Sprint Planning)活动 ...

  7. Java基础之原生JDBC操作数据库

    前言 日常开发中,我们都习惯了使用ORM框架来帮我们操作数据库,本文复习.记录Java如何使用原生JDBC操作数据库 代码编写 封装几个简单方法 find查询方法 findOne查询方法 update ...

  8. (二)、Docker 快速入门

    文档:https://docs.docker.com/install/linux/docker-ce/centos/ 中文文档:https://docs.docker-cn.com/engine/in ...

  9. 【BZOJ-2199】奶牛议会

    链接: BZOJ-2199 题意: 给出 \(n(1\leq n\leq 1000)\) 个点,\(m(1\leq m\leq 4000)\) 个形如:"点 \(a\) 取 \(ca\) 或 ...

  10. SpringCloud微服务实战——搭建企业级开发框架(十一):集成OpenFeign用于微服务间调用

    作为Spring Cloud的子项目之一,Spring Cloud OpenFeign以将OpenFeign集成到Spring Boot应用中的方式,为微服务架构下服务之间的调用提供了解决方案.首先, ...