「CF85E」 Guard Towers

模拟赛考了这题的加强版

然后我因为初值问题直接炸飞

题目大意:

给你二维平面上的 \(n\) 个整点,你需要将它们平均分成两组,使得每组内任意两点间的曼哈顿距离的最大值最小。

本题数据范围为 $n\le 5\times 10^3 $。

这种极值问题,很容易想到的是二分答案,而本题也确实可行。

二分距离的最大值 \(x\),将两点距离大于 \(x\) 的点对连边,则问题转化为我们构建的新图是否为二分图。

其实我感觉复杂度挺假的


考虑曼哈顿距离在此处处理并不方便,所以我们可以将其转化为切比雪夫距离进行求解。

(定义可以去网上康康)

即令 \((x,y)=(x+y,x-y)\),得到的新的点之间的切比雪夫距离等价于原来的点之间的曼哈顿距离。

曼哈顿距离:\(|x_1-x_2|+|y_1-y_2|\)

切比雪夫距离:\(\max\{|x_1-x_2|,|y_1-y_2|\}\)。

于是现在的问题变为:在平面内用两个相同大小的正方形覆盖所有点的最小正方形大小。

首先,平面上的所有点可以被一个最小的矩形覆盖,那么根据切比雪夫距离的定义,两个正方形的某一个顶点必定与矩形的某个顶点重合,因为这个矩形的每条边上都有点的存在。

也就是说,我们找到的两个正方形一定长这样:

如图所示共有两种情况需要讨论。

那么问题就非常简单了:我们枚举每个点,比较重合端点与该点的距离,以决定该点的归属。

这样我们可以在线性时间内找到两种情况的答案,比较即可。

这样我们解决了第一问,即每个正方形的大小。

如何统计方案数?

首先用两种颜色染色就有两种染色方案。

然后最后我们找到的正方形可能长这样:

红色部分的点可以被任意分配,每个点有两种情况,假设共有 \(x\) 个点,就有 \(2^x\) 种分配方案。

现在仍然有一个棘手的问题,如果刚才的两种情况得到的答案大小相等怎么办?

将最终答案乘二即可。

但是,仍然存在特殊情况。

当得到的正方形是这个样子的时候,我们上面讨论的两种情况是一样的,这个时候答案不需要发生改变。

综上,我们在 \(O(n)\) 的时间复杂度内解决了此问题。

(代码是考场上写的改的,真的很丑)

#include<bits/stdc++.h>
using namespace std;
const int maxn=1e6+5;
const int p=1e9+7;
int x[maxn],y[maxn];
int X1=36456,X2=-4746,y3=34563,y4=-2345234;//看这个地方就知道我的心情有多复杂...
int dist(int X1,int Y1,int X2,int Y2){
return max(abs(X1-X2),abs(Y1-Y2));
}
int Ans=-1,Cnt,n,mx,cnt;
int ksm(int a,int b,int p){
int ans=1;
while(b){
if(b&1) ans=1ll*ans*a%p;
b>>=1,a=1ll*a*a%p;
}
return ans;
}
void calc(){
mx=0,cnt=0;
for(int i=1;i<=n;++i){
mx=max(mx,min(dist(x[i],y[i],X1,y3),dist(x[i],y[i],X2,y4)));
}
for(int i=1;i<=n;++i){
if(dist(x[i],y[i],X1,y3)<=mx&&dist(x[i],y[i],X2,y4)<=mx) ++cnt;
}
if(Ans==-1) Ans=mx,Cnt=cnt;
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0),cout.tie(0);
cin>>n;
if(n==2) cout<<"0\n2\n",exit(0);
for(int i=1;i<=n;++i){
int a,b;cin>>a>>b;
x[i]=a+b;
y[i]=a-b;
}
for(int i=1;i<=n;++i){
if(x[i]<X1) X1=x[i];
if(x[i]>X2) X2=x[i];
if(y[i]<y3) y3=y[i];
if(y[i]>y4) y4=y[i];
}
calc();
swap(y3,y4);
calc();
swap(y3,y4);
if(mx<Ans){
cout<<mx<<'\n'<<ksm(2,1+cnt,p)<<'\n';
}
else if(mx==Ans){
cnt=0;
for(int i=1;i<=n;++i){
if(dist(x[i],y[i],X1,y3)<=mx&&dist(x[i],y[i],X2,y4)<=mx) ++cnt;
else if(dist(x[i],y[i],X1,y4)<=mx&&dist(x[i],y[i],X2,y3)<=mx) ++cnt;
}
if(X2-X1>mx&&y4-y3>mx) cout<<mx<<'\n'<<ksm(2,2+cnt,p)<<'\n';
else cout<<mx<<'\n'<<ksm(2,1+cnt,p)<<'\n';
}
else cout<<Ans<<'\n'<<ksm(2,1+Cnt,p)<<'\n';
return 0;
}

「CF85E」 Guard Towers的更多相关文章

  1. [CF85E] Guard Towers - 二分+二分图

    题目描述 In a far away kingdom lives a very greedy king. To defend his land, he built n n n guard towers ...

  2. 「译」JUnit 5 系列:条件测试

    原文地址:http://blog.codefx.org/libraries/junit-5-conditions/ 原文日期:08, May, 2016 译文首发:Linesh 的博客:「译」JUni ...

  3. 「译」JUnit 5 系列:扩展模型(Extension Model)

    原文地址:http://blog.codefx.org/design/architecture/junit-5-extension-model/ 原文日期:11, Apr, 2016 译文首发:Lin ...

  4. JavaScript OOP 之「创建对象」

    工厂模式 工厂模式是软件工程领域一种广为人知的设计模式,这种模式抽象了创建具体对象的过程.工厂模式虽然解决了创建多个相似对象的问题,但却没有解决对象识别的问题. function createPers ...

  5. 「C++」理解智能指针

    维基百科上面对于「智能指针」是这样描述的: 智能指针(英语:Smart pointer)是一种抽象的数据类型.在程序设计中,它通常是经由类型模板(class template)来实做,借由模板(tem ...

  6. 「JavaScript」四种跨域方式详解

    超详细并且带 Demo 的 JavaScript 跨域指南来了! 本文基于你了解 JavaScript 的同源策略,并且了解使用跨域跨域的理由. 1. JSONP 首先要介绍的跨域方法必然是 JSON ...

  7. 「2014-5-31」Z-Stack - Modification of Zigbee Device Object for better network access management

    写一份赏心悦目的工程文档,是很困难的事情.若想写得完善,不仅得用对工具(use the right tools),注重文笔,还得投入大把时间,真心是一件难度颇高的事情.但,若是真写好了,也是善莫大焉: ...

  8. 「2014-3-18」multi-pattern string match using aho-corasick

    我是擅(倾)长(向)把一篇文章写成杂文的.毕竟,写博客记录生活点滴,比不得发 paper,要求字斟句酌八股结构到位:风格偏杂文一点,也是没人拒稿的.这么说来,arxiv 就好比是 paper 世界的博 ...

  9. 「2014-3-17」C pointer again …

    记录一个比较基础的东东-- C 语言的指针,一直让人又爱又恨,爱它的人觉得它既灵活又强大,恨它的人觉得它太过于灵活太过于强大以至于容易将人绕晕.最早接触 C 语言,还是在刚进入大学的时候,算起来有好些 ...

随机推荐

  1. 八、.net core(.NET 6)配置读取appsettings文件内容的通用功能

     添加通用读取配置文件功能 在Wsk.Core.Package项目下,新增Microsoft.Extensions.Configuration包: 在启动项目下,设置appsettings.json属 ...

  2. Selenium3自动化测试【18】XPath定位元素(2)

    层级与属性结合定位 如果被定为的元素,无法通过自身属性来唯一标识自己,此时可以考虑借助上级元素来定位自己.举生活中的例子,一个婴儿刚出生,还没有姓名与身份证号,此时给婴儿进行检查时往往会标注为&quo ...

  3. 痞子衡嵌入式:在SBL项目实战中妙用i.MXRT1xxx里SystemReset不复位的GPR寄存器

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家介绍的是i.MXRT1xxx里SystemReset不复位的GPR寄存器的小妙用. 我们知道稍大规模的项目代码设计一般都是多人协作完成的,在项目 ...

  4. docker部署node.js

    1.dockerfile FROM node:14.16.0 RUN mkdir -p /var/log/lily/ RUN mkdir -p /opt/node # 工作目录 WORKDIR /op ...

  5. Docker学习(13) Docker容器的网络连接

    Docker容器的网络连接 Docker容器的网络基础 先安装网桥管理工具 Docker容器的互联 默认 Docker容器与外部网络的连接

  6. BTC芯片介绍

    BTC芯片介绍 Innosilicon宣布全球第一和最佳的28nm比特币ASIC和参考矿机 A1Craft(也称为A1)是2013年世界上最好的BTC ASIC,这是比特币区块哈希算法的易于使用,定制 ...

  7. 将代码生成器带入TVM

    将代码生成器带入TVM 为了使数据科学家不必担心开发新模型时的性能,硬件后端提供程序(例如Intel,NVIDIA,ARM等)可以提供诸如cuBLAS或cuDNN之类的内核库以及许多常用的深度学习内核 ...

  8. YOLO v1到YOLO v4(下)

    YOLO v1到YOLO v4(下) Faster YOLO使用的是GoogleLeNet,比VGG-16快,YOLO完成一次前向过程只用8.52 billion 运算,而VGG-16要30.69bi ...

  9. 深度学习调用TensorFlow、PyTorch等框架

    深度学习调用TensorFlow.PyTorch等框架 一.开发目标目标 提供统一接口的库,它可以从C++和Python中的多个框架中运行深度学习模型.欧米诺使研究人员能够在自己选择的框架内轻松建立模 ...

  10. 如何在TVM上集成Codegen(上)

    如何在TVM上集成Codegen(上) 许多常用的深度学习内核,或者提供DNNL或TensorRT等框架和图形引擎,让用户以某种方式描述他们的模型,从而获得高性能.此外,新兴的深度学习加速器也有自己的 ...