城市正视图(Urban Elevations, ACM/ICPC World Finals 1992, UVa221)rust解法

news2024/11/17 7:33:48

如图5-4所示,有n(n≤100)个建筑物。左侧是俯视图(左上角为建筑物编号,右下角为高度),右侧是从南向北看的正视图。
在这里插入图片描述
输入每个建筑物左下角坐标(即x、y坐标的最小值)、宽度(即x方向的长度)、深度(即y方向的长度)和高度(以上数据均为实数),输出正视图中能看到的所有建筑物,按照左下角x坐标从小到大进行排序。左下角x坐标相同时,按y坐标从小到大排序。输入保证不同的x坐标不会很接近(即任意两个x坐标要么完全相同,要么差别足够大,不会引起精度问题)。
【分析】
注意到建筑物的可见性等价于南墙的可见性,可以在输入之后直接忽略“深度”这个参数。
把所有建筑物按照左下角坐标排序,然后依次判断可见性。
判断可见性看上去比较麻烦,因为一个建筑物可能只有部分可见,无法枚举所有x坐标,因为x坐标是实数,所以有无穷多个。
解决方法是离散化,即把无穷变为有限。就是把每一个建筑物的两端的坐标x和x+w放进一个数组里,然后排序并去重,做完这些操作就相当于分割了如下的若干个区间。

区间具有如下性质:
1.该区间要么不存在建筑物,要么存在若干个建筑物。
2.在区间中的建筑物,一定会把区间给填满,不会出现建筑物只占区间部分空间的情况。
所以我们只需要对每个建筑物,检查每个区间,判断它是否在该区间中。根据区间性质,只需在这个区间里任选一个点(例如中点),就能判断出一个建筑物是否在整个区间内。如果建筑物在该区间中,那么再检查它前面是否有一个比它更高的在该区间的建筑物。

样例:
输入

14
160 0 30 60 30
125 0 32 28 60
95 0 27 28 40
70 35 19 55 90
0 0 60 35 80
0 40 29 20 60
35 40 25 45 80
0 67 25 20 50
0 92 90 20 80
95 38 55 12 50
95 60 60 13 30
95 80 45 25 50
165 65 15 15 25
165 85 10 15 35

输出

5
9
4
3
10
2
1
14

解法:

use std::io;
#[derive(Debug, Clone, Copy)]
struct Building {
    pos: (f64, f64),
    w: f64,
    d: f64,
    h: f64,
    id: usize,
}
fn main() {
    let mut buf = String::new();
    io::stdin().read_line(&mut buf).unwrap();
    let n: usize = buf.trim().parse().unwrap();
    let mut buildings: Vec<Building> = vec![];
    let mut xpoint: Vec<f64> = vec![];
    for i in 0..n {
        let mut buf = String::new();
        io::stdin().read_line(&mut buf).unwrap();
        let v: Vec<f64> = buf.split_whitespace().map(|e| e.parse().unwrap()).collect();
        let b = Building {
            pos: (v[0], v[1]),
            w: v[2],
            d: v[3],
            h: v[4],
            id: i + 1,
        };
        buildings.push(b);
        xpoint.push(b.pos.0);
        xpoint.push(b.pos.0 + b.w);
    }
    //println!("{:?}", buildings);
    buildings.sort_by(|a, b| a.pos.partial_cmp(&b.pos).unwrap());
    xpoint.sort_by(|a, b| a.partial_cmp(b).unwrap());
    xpoint.dedup();
    //println!("{:?}", buildings);
    //println!("{:?}", xpoint);
    for i in 0..n {
        let mut bvis = false;
        for j in 0..xpoint.len() - 1 {
            if is_visible(&buildings, i, (xpoint[j], xpoint[j + 1])) {
                bvis = true;
                break;
            }
        }
        if bvis {
            println!("{}", buildings[i].id);
        }
    }
}

fn is_visible(buildings: &Vec<Building>, i: usize, interval: (f64, f64)) -> bool {
    if !is_in_interval(buildings, i, interval) {
        return false;
    }
    for k in 0..buildings.len() {
        if buildings[i].pos.1 > buildings[k].pos.1
            && buildings[i].h <= buildings[k].h
            && is_in_interval(buildings, k, interval)
        {
            return false;
        }
    }
    return true;
}
fn is_in_interval(buildings: &Vec<Building>, i: usize, interval: (f64, f64)) -> bool {
    let mid = (interval.0 + interval.1) / 2.0;
    return mid >= buildings[i].pos.0 && mid <= buildings[i].pos.0 + buildings[i].w;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1118781.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

华山论剑:2nm芯片工艺谁更强?

在当今高速发展的科技时代&#xff0c;芯片工艺的重要性不言而喻。芯片制造技术不断突破&#xff0c;使得电子产品性能更高、功能更强大&#xff0c;同时也推动了整个科技行业的快速发展。本文探讨下三星、台积电和英特尔三大芯片制造巨头的工艺技术。 英特尔未来几年的主要目标…

Github Actions实现Spring Boot自动化部署(第二弹)

Github Actions实现Spring Boot自动化部署&#xff08;第二弹&#xff09; 前言 ​ 今天就来讲述一下如何使用GitHub结合Actions实现Spring Boot程序从提交代码到打包、容器化、部署全过程自动化。首先咱们得现有一个能够在本地运行的Spring Boot程序&#xff0c;并且在Githu…

3D测量之圆孔测量 拟合圆 点云变换

0. 效果展示 1. 圆孔测量介绍 此文中的圆孔测量是一项3D视觉技术,旨在精确测量物体表面上的圆孔的直径和中心坐标。通过使用高精度3D相机(线激光轮廓仪或结构体等)采集原始点云数据,通过3D视觉算法能够快速、准确地分析物体上的圆孔特征,为制造和工程领域提供了强大的测量…

FFT64点傅里叶变换verilog蝶形运算,代码和视频

名称&#xff1a;FFT64点verilog傅里叶变换 软件&#xff1a;Quartus 语言&#xff1a;Verilog 代码功能&#xff1a; 使用verilog代码实现64点FFT变换&#xff0c;使用蝶形运算实现傅里叶变换 演示视频&#xff1a;http://www.hdlcode.com/index.php?mhome&cView&…

SpringCloud学习笔记(上):服务注册与发现:Eureka、Zookeeper、Consul+负载均衡服务调用:Ribbon

壹、零基础 一、微服务架构零基础理论入门 SpringCloud分布式微服务架构的一站式解决方案&#xff0c;是多种微服务架构落地技术的集合体&#xff0c;俗称微服务全家桶。 二、从2.2.x和H版开始说起 springboot版本选择&#xff1a; git源码地址&#xff1a;https://github.…

渗透测试工具(3)Burpsuite

笔记目录 渗透测试工具(1)wireshark渗透测试工具(2)Nmap渗透测试工具(3)Burpsuite 1.简介 是Web应用程序测试&#xff0c;请求的拦截和修改,扫描web应用程序漏洞,以暴力破解登陆表单,执行会话令牌等多种的随机性检查。 (1)模块介绍 ①Intercept&#xff1a;用于显示和修改Ht…

Java面试题-UDP\TCP\HTTP

UDP UDP特性 &#xff08;1&#xff09;UDP是无连接的&#xff1a;发送数据之前不需要像TCP一样建立连接&#xff0c;也不需要释放连接&#xff0c;所以减少了发送和接收数据的开销 &#xff08;2&#xff09;UDP 使用尽最大努力交付&#xff1a;即不保证可靠交付 &#xff0…

FGSM快速梯度符号法非定向攻击代码(PyTorch)

数据集&#xff1a;手写字体识别MNIST 模型&#xff1a;LeNet import torch.nn as nn import torch.nn.functional as F import torch from torchvision import datasets, transforms import matplotlib.pyplot as plt use_cuda True device torch.device("cuda"…

密码登录虽安全,但有时很麻烦!如何禁用或删除Windows 11中的密码登录

如果你想在Windows 11上自动登录,在本指南中,我们将向你展示如何删除你的帐户密码。 在Windows 11上,你可以至少通过三种方式从帐户中删除登录密码。在你的帐户上使用密码有助于保护你的计算机和文件免受来自internet或本地的未经授权的访问。然而,在某些情况下,密码可能…

Python语言:元组的使用

元组是存放一个有序的不可改变内容的的容器。 元组的特点&#xff1a; 他不能修改元素。元组的元素由小括号括起来&#xff0c;元素之间用逗号隔开。元组可以保存许多相同内容的元素。元组元素里可以嵌套元组也可以嵌套其他类型的容器。 元组的定义与创建 # 创建一个元组&am…

文件的物理结构(连续分配,链接分配,索引分配)

1.文件块&#xff0c;磁盘块 类似于内存分页&#xff0c;磁盘中的存储单元也会被分为一个个“块/磁盘块/物理块”。 很多操作系统中&#xff0c;磁盘块的大小与内存块、页面的大小相同。 内存与磁盘之间的数据交换&#xff08;即读/写操作、磁盘I/O&#xff09;都是以“块”为…

QTday05(TCP的服务端客户端通信)

实现聊天室功能 服务端代码&#xff1a; pro文件需要导入 network 头文件&#xff1a; #ifndef WIDGET_H #define WIDGET_H#include <QWidget> #include <QTcpServer>//服务端 #include <QTcpSocket>//客户端 #include <QList> #include <QMes…

【代码随想录】算法训练营 第十一天 第五章 栈与队列 Part 2

20. 有效的括号 题目 给定一个只包括 (&#xff0c;)&#xff0c;{&#xff0c;}&#xff0c;[&#xff0c;] 的字符串 s &#xff0c;判断字符串是否有效。 有效字符串需满足&#xff1a; 左括号必须用相同类型的右括号闭合。左括号必须以正确的顺序闭合。每个右括号都有一…

FL Studio2024破解版水果注册机

我们都知道&#xff0c;FL Studio是一款非常好用的音乐编曲软件。随着商业音乐的兴起&#xff0c;编曲这一词汇逐渐被大家所熟知&#xff0c;而有些小伙伴可能也听说过编曲是由四大件进行编写的&#xff0c;所以今天就和大家分享一下&#xff0c;编曲中的四大件是什么&#xff…

Springboot整合Redis的Cluster集群进行API限流

Redis天生就是限流的好帮手&#xff01;因为它有key&#xff0c;有value&#xff0c;有expire过期时间。我们把ip和url作为表示某个接口的key&#xff0c;而value就是这个ip下访问该url接口的次数&#xff0c;过期时间就是设定的限时时间。 我们把限时时间设定为3s&#xff0c…

一、2023 CISSP认证介绍

目录 1.CISSP概况 2.CISSP考题分析 3.备考建议 1.CISSP概况 参考:

【C++代码】二叉搜索树的最近公共祖先,二叉搜索树中的插入操作,删除二叉搜索树中的节点--代码随想录

题目&#xff1a;二叉搜索树的最近公共祖先 给定一个二叉搜索树, 找到该树中两个指定节点的最近公共祖先。最近公共祖先的定义为&#xff1a;“对于有根树 T 的两个结点 p、q&#xff0c;最近公共祖先表示为一个结点 x&#xff0c;满足 x 是 p、q 的祖先且 x 的深度尽可能大&a…

Catalan 数 和 Stirling 数

这个也可以理解为栈&#xff0c;用 ( 表示 入栈 &#xff0c; ) 表示出栈 , 任何情况下表示入栈的 ( 都必须大于等于 ) 的个数 这个思路和入栈出栈的思路是等价的

2.1.C++项目:网络版五子棋对战之前置知识

文章目录 一、Websocketpp&#xff08;一&#xff09;Websocket介绍&#xff08;二&#xff09;报文格式&#xff08;三&#xff09;Websocketpp介绍&#xff08;四&#xff09;Websocketpp使用1.websocketpp常用接口介绍2. http/websocket服务器 &#xff08;五&#xff09;Js…

Vue基础与常用指令,Element基础

1.vue快速入门 vue概述 Vue是一套构建用户界面的渐进式前端框架 只关注视图层&#xff0c;并且非常容易学习&#xff0c;还可以很方便的与其它库或已有项目整合 通过尽可能简单的API来实现响应数据的绑定和组合的视图组件 特点 易用&#xff1a;在有HTMLCSSJavaScript的基…