P4005 小 Y 和地铁
题目描述
小 Y 是一个爱好旅行的 OIer。一天,她来到了一个新的城市。由于不熟悉那里的交通系统,她选择了坐地铁。
她发现每条地铁线路可以看成平面上的一条曲线,不同线路的交点处一定会设有
换乘站 。通过调查得知,没有线路是环线,也没有线路与自身相交。任意两条不同的线路只会在若干个点上相交,没有重合的部分,且没有三线共点的情况。即,如图所示的情况都是不存在的:
小 Y 坐着地铁 0 号线,路上依次经过了 n 个换乘站。她记下了每个换乘站可以换乘的线路编号,发现每条线路与她所乘坐的线路最多只有 2 个换乘站。现在小 Y 想知道,除掉她经过的换乘站以外,这个城市里最少有几个换乘站。只有你告诉她正确的答案,她才会答应下次带你去玩呢。
输入输出格式
输入格式:
从文件 metro.in 中读入数据。
请.注.意.本.题.有.多.组.输.入.数.据。
输入数据的第一行是一个整数 T,表示输入数据的组数。接下来依次给出每组数据。
对于每组数据,第一行是一个整数 n,表示小 Y 经过的换乘站的数目。第二行为 n个用空格隔开的整数,依次表示每个换乘站的可以换乘的线路编号。这些编号都在 1 ~n 之内。
输出格式:
输出到文件 metro.out 中。
对于每组输入数据,输出一行一个整数,表示除掉这 n 个换乘站之外,最少有几个换乘站。
输入输出样例
4
4
1 2 1 2
8
1 2 3 4 1 2 3 4
5
5 4 3 3 5
8
1 2 3 4 1 3 2 4
0
0
0
1
说明
【样例 1 解释】
对于样例的前两组数据,一种可能的最优答案如下图所示。
【子任务】
一共有 50 个测试点,每个测试点 2 分。你只有在答案完全正确时才能得到该测试点的全部分数,否则不得分。
对于所有测试点,以及对于样例, 1 ≤ T ≤ 100; 1 ≤ n ≤ 44。对于每个测试点, n 的范围如下表:
Solution:
本题ZYYS,绝世搜索好题。
题意有些晦涩,总结后不难发现实际路线只有$4$种情况:
至于洛谷题解中的开始8种情况的另外4种,贪心的想到,完全没有必要那样建,比如:
和
由于要使各曲线的交点尽量少,那么上面两幅图肯定是没有这幅图优秀的:
然后在最上面说的4种情形中,由于上部的曲线不可能和下部的曲线相交,所以可以将其上下分开看,而既有上部又有下部的图直接将其当作两个部分的曲线合并,比如:
理解为上部的曲线$[l,n]$+下部的曲线$[r,n]$就好了。
然后对于同上或同下的两个曲线$[l1,r1],[l2,r2]$,显然只有$l2\leq r1\leq r2$时才会有交点,那么计算一段曲线会产生多少交点,就得统计区间$[l,r]$之间的已有$r$个数,单点修改区间查询直接想到树状数组。
这样就能直接暴力搜索,枚举每条曲线的形态,对于既有上部和下部的曲线,发现可以和另一条单部曲线合并成环,比如:从左到右枚举曲线状态,当前状态只受左边的影响,由于$l$左边的曲线状态已确定,而$r$是确定的,所以当前$[l,r]$的最优情况直接贪心选择两种方式的与左边交点的最小个数就好了,另一种情况同理就好了。
时间复杂度$O(2^{\frac{n}{2}}\log n)$。
代码:
/*Code by 520 -- 9.2*/
#include<bits/stdc++.h>
#define il inline
#define ll long long
#define RE register
#define For(i,a,b) for(RE int (i)=(a);(i)<=(b);(i)++)
#define Bor(i,a,b) for(RE int (i)=(b);(i)>=(a);(i)--)
using namespace std;
const int N=;
int n,a[N],T,l[N],r[N],ans,num;
struct node{
int c[N];
void clear(){memset(c,,sizeof(c));}
void add(int x,int k){while(x<=n)c[x]+=k,x+=x&-x;}
int sum(int x){int ans=;while(x)ans+=c[x],x-=x&-x;return ans;}
int query(int l,int r){return sum(r)-sum(l-);}
}up,down; int gi(){
int a=;char x=getchar();
while(x<''||x>'')x=getchar();
while(x>=''&&x<='')a=(a<<)+(a<<)+(x^),x=getchar();
return a;
} void dfs(int x,int tot){
if(x>num){ans=min(ans,tot);return;}
if(tot>=ans)return;
int upp=min(up.query(l[x],r[x]),down.query(l[x],n)+up.query(r[x],n));
up.add(r[x],),dfs(x+,tot+upp),up.add(r[x],-);
int downn=min(down.query(l[x],r[x]),up.query(l[x],n)+down.query(r[x],n));
down.add(r[x],),dfs(x+,tot+downn),down.add(r[x],-);
} il void solve(){
for(T=gi();T;--T){
scanf("%d",&n),ans=0x7fffffff,num=;
For(i,,n) a[i]=gi();
For(i,,n) For(j,i+,n) if(a[i]==a[j]){l[++num]=i,r[num]=j;break;}
up.clear(),down.clear();
dfs(,);
printf("%d\n",ans);
}
} int main(){
solve();
return ;
}
P4005 小 Y 和地铁的更多相关文章
- 【洛谷4005】小Y和地铁(搜索)
[洛谷4005]小Y和地铁(搜索) 题面 洛谷 有点长. 题解 首先对于需要被链接的两个点,样例中间基本上把所有的情况都给出来了. 但是还缺了一种从下面绕道左边在从整个上面跨过去在从右边绕到下面来的情 ...
- 【清华集训 2017】小Y的地铁 [模拟退火]
小Y的地铁 Time Limit: 50 Sec Memory Limit: 256 MB Description Input Output 对于每组输入数据,输出一行一个整数,表示除掉这 n 个换 ...
- [LOJ#2323]「清华集训 2017」小Y和地铁
[LOJ#2323]「清华集训 2017」小Y和地铁 试题描述 小Y是一个爱好旅行的OIer.一天,她来到了一个新的城市.由于不熟悉那里的交通系统,她选择了坐地铁. 她发现每条地铁线路可以看成平面上的 ...
- 【luogu P4005 清华集训2017】小Y和地铁
题目描述 小 Y 是一个爱好旅行的 OIer.一天,她来到了一个新的城市.由于不熟悉那里的交通系统,她选择了坐地铁. 她发现每条地铁线路可以看成平面上的一条曲线,不同线路的交点处一定会设有 换乘站 . ...
- 【清华集训】小Y和地铁
图已挂,前往luogu 题目: 小 $\rm Y$ 是一个爱好旅行的 $\rm OIer$.一天,她来到了一个新的城市.由于不熟悉那里的交通系统,她选择了坐地铁.她发现每条地铁线路可以看成平面上的一条 ...
- [luogu4005]小Y和地铁【搜索+树状数组】
传送门:https://www.luogu.org/problemnew/show/P4005 最简单的暴力拿最高的分,二进制爆搜. #include <bits/stdc++.h> #d ...
- 清华集训2017D2T1 小 Y 和地铁(metro)
题目:https://www.luogu.org/problem/show?pid=P4005 题意:一条线段,给定n个点(n<=44)其中每个点可能对应另外一个点.如果一个点有对应点,那么就要 ...
- [清华集训2017]小 Y 和地铁(神奇思路,搜索,剪枝,树状数组)
世界上最不缺的就是好题. 首先考虑暴搜.(还有什么题是从这东西推到正解的……) 首先单独一个换乘站明显没用,只用考虑一对对的换乘站. 那么有八种情况:(从题解偷图) 然后大力枚举每个换 ...
- LOJ2323. 「清华集训 2017」小 Y 和地铁 【搜索】【思维】【好】
LINK 思路 首先如果直接算每一个段有三个决策 左/右 上/下 跨不跨过端点 这样的复杂度是\((2^3)^{22}\),显然是无法接受的 然后考虑怎么优化这个东西 首先左右这个决策是没有意义的 因 ...
随机推荐
- html查漏补缺之meta标签
什么是meta标签? meta标签是html标记head区的一个关键标签,它位于HTML文档的<head>和<title>之间(有些也不是在<head>和<t ...
- 使用phpMyAdmin管理网站数据库(创建、导入、导出…)
作为一名站长,最重视的就是网站的数据安全了.本节襄阳网站优化就来讲讲如何使用phpMyAdmin管理软件进行mysql数据库的管理,实现基本的数据库管理用户.数据库的创建.数据的导入和导出操作(网站备 ...
- Web全景图的原理及实现
全景图的基本原理 全景图是一种广角图.通过全景播放器可以让观看者身临其境地进入到全景图所记录的场景中去.比如像是这个.这种看起来很高大上的效果其实背后的原理并不复杂. 通常标准的全景图是一张2:1的图 ...
- python3【基础】-list&tuple
一.list概述 list (列表)是python中最常用的数据类型之一,通过列表可以对数据实现最方便的存储,修改等操作.在python3中,list支持如下方法: Help on class lis ...
- C++ STL中的Binary search(二分查找)
这篇博客转自爱国师哥,这里给出连接https://www.cnblogs.com/aiguona/p/7281856.html 一.解释 以前遇到二分的题目都是手动实现二分,不得不说错误比较多,关于返 ...
- c# 画image
这是一个例子,从数据库中读取然后赋伪彩,生成bitmap,给到imagebox控件(其image属性为平铺). https://pan.baidu.com/s/1hf_fGFHjGoDK_gywuhg ...
- Eclipse/myEclipse 代码提示/自动提示/自动完成设置(转)
一.设置超级自动提示 设置eclipse/myEclipse代码提示可以方便开发者,不用在记住拉杂的单词,只用打出首字母,就会出现提示菜单.如同dreamweaver一样方便. 1.菜单window- ...
- 【技术向】rainmeter的设计与发现
我们在大学期间所学的那点代码知识还远远不够,于是我就自己寻找到了一款简单易懂的软件,来丰富我的代码知识. 这款软件叫rainmeter,中文叫做雨滴,是一款可以修改桌面的软件.它可以将桌面上更改出硬盘 ...
- C#中委托的理解
请注意,这只是个人关于C#中委托的一点点理解,参考了一些博客,如有不周之处,请指出,谢谢! 委托是一种函数指针,委托是方法的抽象,方法是委托的实例.委托是C#语言的一道坎,明白了委托才能算是C#真正入 ...
- c#程序的阅读
1 .程序是为表示两个连续的整数不能被整除. 2 ,3 程序黑框得不出结果,所以不知道具体的结果和运行时间. 4 采用更好的专用电脑进行计算.