link

考虑二分答案 $F$ ,那么现在的问题变成是否对于覆盖并有交集。

考虑边 $(u,v)$ ,若覆盖并在 $(u,v,w)$ 线段中,设点 $i$ 走到 $u$ 号后还能走 $F1$ , 走到 $v$ 还能走 $F2$ ,则现在要求的是一个子问题:求在 $n$ 个 $(0,F1),(w-F2+1,w)$ 中判断是否有交集,若存在点 $x$ 使得 $n$ 个线段都能被覆盖时,$x$ 肯定为 $F1$ 或 $w-F2+1$ ,所以直接暴力枚举即可,时间复杂度 $O(n^4\log 值域)$。

而如何优化时间复杂度,考虑如何快速计算贡献,直接离散化后差分计算即可。

时间复杂度 $O(n^3\log 值域)$。

#include<iostream>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<climits>
using namespace std;
inline int read(){
int f=,ans=;char c=getchar();
while(c<''||c>''){if(c=='-')f=-;c=getchar();}
while(c>=''&&c<=''){ans=ans*+c-'';c=getchar();}
return f*ans;
}
const int MAXN=;
struct Edge{
int u,v,w;
}x[MAXN*MAXN];
int n,m,dis[MAXN][MAXN];
double f1[MAXN][MAXN*MAXN],f2[MAXN][MAXN*MAXN],l,r,minn=LLONG_MAX,eps=1e-,num[MAXN<<],tmp[MAXN<<];
int M;
int G1[MAXN<<][MAXN<<],G2[MAXN<<][MAXN<<];
int NU[MAXN<<],cnt[MAXN],Cnt;
inline int Q(double res){return lower_bound(tmp+,tmp+M+,res)-tmp;}
inline bool Query(int id,double G){
memset(NU,,sizeof(NU));memset(cnt,,sizeof(cnt));
int Num=;
num[++Num]=;tmp[Num]=num[Num];
num[++Num]=x[id].w;tmp[Num]=num[Num];
for(register int i=;i<=n;i++){
double t1=f1[i][id],t2=x[id].w-f2[i][id];
Cnt++;
if(t1>=) num[++Num]=min(t1,(double)x[id].w),tmp[Num]=num[Num];
if(f2[i][id]>=) num[++Num]=max((double),t2),tmp[Num]=num[Num];
}
sort(tmp+,tmp+Num+);
M=unique(tmp+,tmp+Num+)-tmp-;
for(register int i=;i<=Num;i++) Cnt++,num[i]=lower_bound(tmp+,tmp+M+,num[i])-tmp;
for(register int i=;i<=n;i++){
Cnt++;
double t1=f1[i][id],t2=x[id].w-f2[i][id];
if(t1>=){
int l=,r=Q(min(t1,(double)x[id].w))+;
G1[l][++NU[l]]=i;G2[l][NU[l]]=;
G1[r][++NU[r]]=i;G2[r][NU[r]]=-;
}
if(f2[i][id]>=){
int l=Q(max((double),t2));
G1[l][++NU[l]]=i;G2[l][NU[l]]=;
}
}
int Sum=;
for(register int i=;i<=M;i++){
for(register int j=;j<=NU[i];j++){
Cnt++;
int f=G1[i][j],opt=G2[i][j];
if(opt==){
if(cnt[f]==) Sum++;
cnt[f]++;
}else{
if(cnt[f]==) Sum--;
cnt[f]--;
}
}if(Sum==n) return ;
}return ;
}
inline bool check(double G){
for(register int u=;u<=n;u++){
for(register int i=;i<=m;i++){
f1[u][i]=G-dis[u][x[i].u];
f2[u][i]=G-dis[u][x[i].v];
}
}
for(register int i=;i<=m;i++)
if(Query(i,G)) return ;
return ;
}
int main(){
// freopen("make.in","r",stdin);
n=read(),m=read();
memset(dis,/,sizeof(dis));
for(int i=;i<=m;i++){
int u=read(),v=read(),w=read();
r+=w;
x[i].u=u,x[i].v=v,x[i].w=w;
dis[u][v]=dis[v][u]=w;
}
for(int i=;i<=n;i++) dis[i][i]=;
for(int p=;p<=n;p++)
for(int i=;i<=n;i++)
for(int j=;j<=n;j++)
dis[i][j]=min(dis[i][j],dis[i][p]+dis[p][j]);
while(l<=r){
double mid=(l+r)/2.0;
if(check(mid)) minn=min(minn,mid),r=mid-eps;
else l=mid+eps;
}printf("%.9lf\n",minn);
}

[51Nod2558] 选址的更多相关文章

  1. [NOIP2014] 提高组 洛谷P2038 无线网络发射器选址

    题目描述 随着智能手机的日益普及,人们对无线网的需求日益增大.某城市决定对城市内的公共场所覆盖无线网. 假设该城市的布局为由严格平行的129 条东西向街道和129 条南北向街道所形成的网格状,并且相邻 ...

  2. 基于K2 BPM的大型连锁企业开关店选址管理解决方案

    业内有句名言:“门店最重要的是什么?第一是选址,第二是选址,第三还是选址” 选址是一个很复杂的综合性商业决策过程,需要定性考虑和定向分析.K2开关店&选址管理方案重点关注:如何开出更好的店?在 ...

  3. NOIP2014 无线网络发射器选址

    1.无线网络发射器选址 (wireless.cpp/c/pas) [问题描述] 随着智能手机的日益普及,人们对无线网的需求日益增大.某城市决定对城市内的公共场所覆盖无线网. 假设该城市的布局为由严格平 ...

  4. Codevs 1507 酒厂选址

    1507 酒厂选址 时间限制: 1 s 空间限制: 128000 KB 题目等级 : 黄金 Gold 传送门 题目描述 Description Abstinence(戒酒)岛的居民们酷爱一种无酒精啤酒 ...

  5. BZOJ 1835: [ZJOI2010]base 基站选址 [序列DP 线段树]

    1835: [ZJOI2010]base 基站选址 题目描述 有N个村庄坐落在一条直线上,第i(i>1)个村庄距离第1个村庄的距离为Di.需要在这些村庄中建立不超过K个通讯基站,在第i个村庄建立 ...

  6. 动态规划(斜率优化):[CEOI2004]锯木厂选址

    锯木场选址(CEOI2004) 从山顶上到山底下沿着一条直线种植了n棵老树.当地的政府决定把他们砍下来.为了不浪费任何一棵木材,树被砍倒后要运送到锯木厂. 木材只能按照一个方向运输:朝山下运.山脚下有 ...

  7. Floyd算法应用-医院选址问题

    1)问题描述 n个村庄之间的交通图可以用有向网图来表示,图中边<vi, vj>上的权值表示从村庄i到村庄j的道路长度.现在要从这n个村庄中选择一个村庄新建一所医院,问这所医院应建在哪个村庄 ...

  8. NOIP2014_day2:无线网络发射器选址

    #include<stdio.h>//NOIP2014 day2 :无线网络发射器选址 ,max=; ][]; void wifi(int a,int b,int c) { int i,j ...

  9. 关于NOIP2014“无线网络发射器选址”一题的衍生题目的思考及思维方向

    无线网络发射器选址 题目描述 随着智能手机的日益普及,人们对无线网的需求日益增大.某城市决定对城市内的公共场所覆盖无线网. 假设该城市的布局为由严格平行的129 条东西向街道和129 条南北向街道所形 ...

随机推荐

  1. php 客户端调用elasticsearch接口

    1.php调用elasticsearch接口[参考资料:https://www.cnblogs.com/php0916/articles/6587340.html] /data/www/syhuo.n ...

  2. C# 字符串的长度问题

    string str = "aa奥奥"; 如果直接取 str.length,取的就是字符的长度,一个汉字也是一个字符,长度就是4. 一个汉字是两个字节,如果需要统计字节数,可以用下 ...

  3. find查找多种文件后缀

    find命令最常用的是查找某个文件,如: find ./ -name "test.txt" 则会在当前目录及子目录下查找test.txt文件 更常用的是查找某一类型的文件,如: f ...

  4. UIWebView 禁止检测链接弹出UIActionSheet

    解决方法一: 添加以下代码禁止检测类型 webView.dataDetectorTypes = UIDataDetectorTypeNone; 解决方法二: - (void)webViewDidFin ...

  5. Matlab 读取文件夹里所有的文件

    (image = dir('D:\gesture\*.*'); % dir是指定文件夹得位置,他与dos下的dir用法相同. 用法有三种: 1. dir 是指工作在当前文件夹里 2. dir name ...

  6. 关于openGL、GPUImage、ios直播相关不错的博客

    http://www.jianshu.com/users/815d10a4bdce/latest_articles

  7. 消息队列之 ActiveMQ

    简介 ActiveMQ 特点 ActiveMQ 是由 Apache 出品的一款开源消息中间件,旨在为应用程序提供高效.可扩展.稳定.安全的企业级消息通信. 它的设计目标是提供标准的.面向消息的.多语言 ...

  8. 使用Mybatis执行sql脚本

    pom.xml <?xml version="1.0" encoding="UTF-8"?> <project xmlns="htt ...

  9. Oracle-buffer cache、shared pool

    http://blog.csdn.net/panfelix/article/details/38347059   buffer pool 和shared pool 详解 http://blog.csd ...

  10. 如何让ls按目录和文件 分开进行列表?

    linux的思想是: 有很多 "小工具", 但是功能并不弱的 小工具, 组合起来完成一些复杂的工作, 通过 这些工具的组合可以完成各种各样的, 不同的任务. 如: ls, sort, hea ...