热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

NOIP2018提高组模拟赛8.25-矩阵交集问题

本题涉及矩阵的交集计算,通过排序和权值线段树实现高效求解。

题目描述:

给定多个矩形,每个矩形由其左下角和右上角的坐标定义。任务是找到这些矩形的交集的最大面积。

输入格式:

第一行包含一个整数 T,表示测试数据的组数。对于每组测试数据,第一行包含两个整数 n 和 m,分别表示矩形的数量和允许的最大删除数量。接下来 n 行,每行包含两个整数 x 和 y,表示矩形的宽度和高度。

输出格式:

对于每组测试数据,输出一行,包含一个整数,表示所有矩形交集的最大面积。

数据范围:

1 ≤ T ≤ 10,1 ≤ n ≤ 10^5,1 ≤ m ≤ n,1 ≤ x, y ≤ 10^5。

分析:

所有矩形的交集最大面积可以通过计算所有矩形宽度和高度的最小值来确定,即 min(x) * min(y)。为了高效地解决这个问题,我们首先按照矩形的宽度进行排序,然后使用一个权值线段树来维护高度信息。具体步骤如下:

  1. 对所有矩形按宽度从小到大排序。
  2. 遍历排序后的矩形,使用权值线段树记录每个矩形的高度。
  3. 在遍历过程中,动态维护当前剩余矩形的高度最小值,并计算当前矩形的宽度与高度最小值的乘积,更新答案。

代码实现:

#include 
#include
#define LL long long
const int maxn = 1e5 + 7;
const int maxp = 1e5;
using namespace std;

int test, n, m;
int t[maxn * 4];
LL ans;

struct Node {
int x, y;
} a[maxn];

bool cmp(Node x, Node y) {
return x.x }

void update(int p, int l, int r, int x, int k) {
if (l == r) {
t[p] += k;
return;
}
int mid = (l + r) / 2;
if (x <= mid) update(p * 2, l, mid, x, k);
else update(p * 2 + 1, mid + 1, r, x, k);
t[p] = t[p * 2] + t[p * 2 + 1];
}

int getRank(int p, int l, int r, int k) {
if (l == r) return l;
int mid = (l + r) / 2;
if (k <= t[p * 2]) return getRank(p * 2, l, mid, k);
else return getRank(p * 2 + 1, mid + 1, r, k - t[p * 2]);
}

int main() {
freopen("d.in", "r", stdin);
freopen("d.out", "w", stdout);
scanf("%d", &test);
while (test--) {
scanf("%d%d", &n, &m);
for (int i = 1; i <= n; i++) {
scanf("%d%d", &a[i].x, &a[i].y);
}
sort(a + 1, a + n + 1, cmp);
ans = 0;
for (int i = n; i > 0; i--) {
update(1, 1, maxp, a[i].y, 1);
if (i - 1 > m) continue;
int d = getRank(1, 1, maxp, m - (i - 1) + 1);
ans = max(ans, (LL)a[i].x * (LL)d);
}
for (int i = 1; i <= n; i++) update(1, 1, maxp, a[i].y, -1);
printf("%lld\n", ans);
}
return 0;
}

推荐阅读
  • 本文将介绍如何编写一些有趣的VBScript脚本,这些脚本可以在朋友之间进行无害的恶作剧。通过简单的代码示例,帮助您了解VBScript的基本语法和功能。 ... [详细]
  • 本文详细解析了Python中的os和sys模块,介绍了它们的功能、常用方法及其在实际编程中的应用。 ... [详细]
  • 扫描线三巨头 hdu1928hdu 1255  hdu 1542 [POJ 1151]
    学习链接:http:blog.csdn.netlwt36articledetails48908031学习扫描线主要学习的是一种扫描的思想,后期可以求解很 ... [详细]
  • 题目Link题目学习link1题目学习link2题目学习link3%%%受益匪浅!-----&# ... [详细]
  • 本文详细探讨了KMP算法中next数组的构建及其应用,重点分析了未改良和改良后的next数组在字符串匹配中的作用。通过具体实例和代码实现,帮助读者更好地理解KMP算法的核心原理。 ... [详细]
  • 本文介绍如何使用Objective-C结合dispatch库进行并发编程,以提高素数计数任务的效率。通过对比纯C代码与引入并发机制后的代码,展示dispatch库的强大功能。 ... [详细]
  • 前言--页数多了以后需要指定到某一页(只做了功能,样式没有细调)html ... [详细]
  • Python自动化处理:从Word文档提取内容并生成带水印的PDF
    本文介绍如何利用Python实现从特定网站下载Word文档,去除水印并添加自定义水印,最终将文档转换为PDF格式。该方法适用于批量处理和自动化需求。 ... [详细]
  • UNP 第9章:主机名与地址转换
    本章探讨了用于在主机名和数值地址之间进行转换的函数,如gethostbyname和gethostbyaddr。此外,还介绍了getservbyname和getservbyport函数,用于在服务器名和端口号之间进行转换。 ... [详细]
  • 本章将深入探讨移动 UI 设计的核心原则,帮助开发者构建简洁、高效且用户友好的界面。通过学习设计规则和用户体验优化技巧,您将能够创建出既美观又实用的移动应用。 ... [详细]
  • 本文探讨了如何在给定整数N的情况下,找到两个不同的整数a和b,使得它们的和最大,并且满足特定的数学条件。 ... [详细]
  • Splay Tree 区间操作优化
    本文详细介绍了使用Splay Tree进行区间操作的实现方法,包括插入、删除、修改、翻转和求和等操作。通过这些操作,可以高效地处理动态序列问题,并且代码实现具有一定的挑战性,有助于编程能力的提升。 ... [详细]
  • 从 .NET 转 Java 的自学之路:IO 流基础篇
    本文详细介绍了 Java 中的 IO 流,包括字节流和字符流的基本概念及其操作方式。探讨了如何处理不同类型的文件数据,并结合编码机制确保字符数据的正确读写。同时,文中还涵盖了装饰设计模式的应用,以及多种常见的 IO 操作实例。 ... [详细]
  • 本文详细介绍了C语言中链表的两种动态创建方法——头插法和尾插法,包括具体的实现代码和运行示例。通过这些内容,读者可以更好地理解和掌握链表的基本操作。 ... [详细]
  • 尽管使用TensorFlow和PyTorch等成熟框架可以显著降低实现递归神经网络(RNN)的门槛,但对于初学者来说,理解其底层原理至关重要。本文将引导您使用NumPy从头构建一个用于自然语言处理(NLP)的RNN模型。 ... [详细]
author-avatar
仰望天空说再见
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有