【二分查找】P9698 [GDCPC2023] Path Planning|普及

本文涉及的基础知识点

本博文代码打包下载

C++二分查找

[GDCPC2023] Path Planning

题面翻译

【题目描述】

有一个 n n n m m m 列的网格。网格里的每个格子都写着一个整数,其中第 i i i 行第 j j j 列的格子里写着整数 a i , j a_{i, j} ai,j。从 0 0 0 ( n × m − 1 ) (n \times m - 1) (n×m1) 的每个整数(含两端)在网格里都恰好出现一次。

( i , j ) (i, j) (i,j) 表示位于第 i i i 行第 j j j 列的格子。您现在需要从 ( 1 , 1 ) (1, 1) (1,1) 出发并前往 ( n , m ) (n, m) (n,m)。当您位于格子 ( i , j ) (i, j) (i,j) 时,您可以选择走到右方的格子 ( i , j + 1 ) (i, j + 1) (i,j+1)(若 j < m j < m j<m),也可以选择走到下方的格子 ( i + 1 , j ) (i + 1, j) (i+1,j)(若 i < n i < n i<n)。

S \mathbb{S} S 表示路径上每个格子里的整数形成的集合,包括 a 1 , 1 a_{1, 1} a1,1 a n , m a_{n, m} an,m。令 mex ( S ) \text{mex}(\mathbb{S}) mex(S) 表示不属于 S \mathbb{S} S 的最小非负整数。请找出一条路径以最大化 mex ( S ) \text{mex}(\mathbb{S}) mex(S),并求出这个最大的值。

【输入格式】

有多组测试数据。第一行输入一个整数 T T T 表示测试数据组数。对于每组测试数据:

第一行输入两个整数 n n n m m m 1 ≤ n , m ≤ 1 0 6 1 \le n, m \le 10^6 1n,m106 1 ≤ n × m ≤ 1 0 6 1 \le n \times m \le 10^6 1n×m106)表示网格的行数和列数。

对于接下来 n n n 行,第 i i i 行输入 m m m 个整数 a i , 1 , a i , 2 , ⋯ , a i , m a_{i, 1}, a_{i, 2}, \cdots, a_{i, m} ai,1,ai,2,,ai,m 0 ≤ a i , j < n × m 0 \le a_{i, j} < n \times m 0ai,j<n×m),其中 a i , j a_{i, j} ai,j 表示格子 ( i , j ) (i, j) (i,j) 里的整数。从 0 0 0 ( n × m − 1 ) (n \times m - 1) (n×m1) 的每个整数(含两端)在网格里都恰好出现一次。

保证所有数据 n × m n \times m n×m 之和不超过 1 0 6 10^6 106

【输出格式】

每组数据输出一行一个整数,表示最大的 mex ( S ) \text{mex}(\mathbb{S}) mex(S)

【样例解释】

对于第一组样例数据,共有 3 3 3 条可能的路径。

  • 第一条路径为 ( 1 , 1 ) → ( 1 , 2 ) → ( 1 , 3 ) → ( 2 , 3 ) (1, 1) \to (1, 2) \to (1, 3) \to (2, 3) (1,1)(1,2)(1,3)(2,3) S = { 1 , 2 , 4 , 5 } \mathbb{S} = \{1, 2, 4, 5\} S={1,2,4,5} 因此 mex ( S ) = 0 \text{mex}(\mathbb{S}) = 0 mex(S)=0
  • 第二条路径为 ( 1 , 1 ) → ( 1 , 2 ) → ( 2 , 2 ) → ( 2 , 3 ) (1, 1) \to (1, 2) \to (2, 2) \to (2, 3) (1,1)(1,2)(2,2)(2,3) S = { 1 , 2 , 0 , 5 } \mathbb{S} = \{1, 2, 0, 5\} S={1,2,0,5} 因此 mex ( S ) = 3 \text{mex}(\mathbb{S}) = 3 mex(S)=3
  • 第三条路径为 ( 1 , 1 ) → ( 2 , 1 ) → ( 2 , 2 ) → ( 2 , 3 ) (1, 1) \to (2, 1) \to (2, 2) \to (2, 3) (1,1)(2,1)(2,2)(2,3) S = { 1 , 3 , 0 , 5 } \mathbb{S} = \{1, 3, 0, 5\} S={1,3,0,5} 因此 mex ( S ) = 2 \text{mex}(\mathbb{S}) = 2 mex(S)=2

因此答案为 3 3 3

对于第二组样例数据,只有 1 1 1 条可能的路径,即 ( 1 , 1 ) → ( 1 , 2 ) → ( 1 , 3 ) → ( 1 , 4 ) → ( 1 , 5 ) (1, 1) \to (1, 2) \to (1, 3) \to (1, 4) \to (1, 5) (1,1)(1,2)(1,3)(1,4)(1,5) S = { 1 , 3 , 0 , 4 , 2 } \mathbb{S} = \{1, 3, 0, 4, 2\} S={1,3,0,4,2} 因此 mex ( S ) = 5 \text{mex}(\mathbb{S}) = 5 mex(S)=5

题目描述

There is a grid with n n n rows and m m m columns. Each cell of the grid has an integer in it, where a i , j a_{i, j} ai,j indicates the integer in the cell located at the i i i-th row and the j j j-th column. Each integer from 0 0 0 to ( n × m − 1 ) (n \times m - 1) (n×m1) (both inclusive) appears exactly once in the grid.

Let ( i , j ) (i, j) (i,j) be the cell located at the i i i-th row and the j j j-th column. You now start from ( 1 , 1 ) (1, 1) (1,1) and need to reach ( n , m ) (n, m) (n,m). When you are in cell ( i , j ) (i, j) (i,j), you can either move to its right cell ( i , j + 1 ) (i, j + 1) (i,j+1) if j < m j < m j<m or move to its bottom cell ( i + 1 , j ) (i + 1, j) (i+1,j) if i < n i < n i<n.

Let S \mathbb{S} S be the set consisting of integers in each cell on your path, including a 1 , 1 a_{1, 1} a1,1 and a n , m a_{n, m} an,m. Let mex ( S ) \text{mex}(\mathbb{S}) mex(S) be the smallest non-negative integer which does not belong to S \mathbb{S} S. Find a path to maximize mex ( S ) \text{mex}(\mathbb{S}) mex(S) and calculate this maximum possible value.

输入格式

There are multiple test cases. The first line of the input contains an integer T T T indicating the number of test cases. For each test case:

The first line contains two integers n n n and m m m ( 1 ≤ n , m ≤ 1 0 6 1 \le n, m \le 10^6 1n,m106, 1 ≤ n × m ≤ 1 0 6 1 \le n \times m \le 10^6 1n×m106) indicating the number of rows and columns of the grid.

For the following n n n lines, the i i i-th line contains m m m integers a i , 1 , a i , 2 , ⋯ , a i , m a_{i, 1}, a_{i, 2}, \cdots, a_{i, m} ai,1,ai,2,,ai,m ( 0 ≤ a i , j < n × m 0 \le a_{i, j} < n \times m 0ai,j<n×m) where a i , j a_{i, j} ai,j indicates the integer in cell ( i , j ) (i, j) (i,j). Each integer from 0 0 0 to ( n × m − 1 ) (n \times m - 1) (n×m1) (both inclusive) appears exactly once in the grid.

It’s guaranteed that the sum of n × m n \times m n×m of all test cases will not exceed 1 0 6 10^6 106.

输出格式

For each test case output one line containing one integer indicating the maximum possible value of mex ( S ) \text{mex}(\mathbb{S}) mex(S).

样例 #1

样例输入 #1

2
2 3
1 2 4
3 0 5
1 5
1 3 0 4 2

样例输出 #1

3
5

提示

For the first sample test case there are 3 3 3 possible paths.

  • The first path is ( 1 , 1 ) → ( 1 , 2 ) → ( 1 , 3 ) → ( 2 , 3 ) (1, 1) \to (1, 2) \to (1, 3) \to (2, 3) (1,1)(1,2)(1,3)(2,3). S = { 1 , 2 , 4 , 5 } \mathbb{S} = \{1, 2, 4, 5\} S={1,2,4,5} so mex ( S ) = 0 \text{mex}(\mathbb{S}) = 0 mex(S)=0.
  • The second path is ( 1 , 1 ) → ( 1 , 2 ) → ( 2 , 2 ) → ( 2 , 3 ) (1, 1) \to (1, 2) \to (2, 2) \to (2, 3) (1,1)(1,2)(2,2)(2,3). S = { 1 , 2 , 0 , 5 } \mathbb{S} = \{1, 2, 0, 5\} S={1,2,0,5} so mex ( S ) = 3 \text{mex}(\mathbb{S}) = 3 mex(S)=3.
  • The third path is ( 1 , 1 ) → ( 2 , 1 ) → ( 2 , 2 ) → ( 2 , 3 ) (1, 1) \to (2, 1) \to (2, 2) \to (2, 3) (1,1)(2,1)(2,2)(2,3). S = { 1 , 3 , 0 , 5 } \mathbb{S} = \{1, 3, 0, 5\} S={1,3,0,5} so mex ( S ) = 2 \text{mex}(\mathbb{S}) = 2 mex(S)=2.

So the answer is 3 3 3.

For the second sample test case there is only 1 1 1 possible path, which is ( 1 , 1 ) → ( 1 , 2 ) → ( 1 , 3 ) → ( 1 , 4 ) → ( 1 , 5 ) (1, 1) \to (1, 2) \to (1, 3) \to (1, 4) \to (1, 5) (1,1)(1,2)(1,3)(1,4)(1,5). S = { 1 , 3 , 0 , 4 , 2 } \mathbb{S} = \{1, 3, 0, 4, 2\} S={1,3,0,4,2} so mex ( S ) = 5 \text{mex}(\mathbb{S}) = 5 mex(S)=5.

二分查找

Can(x)函数: 是否存在某条路径,经过[0…x]所有数字。
将[0…x]的行列号放到v中,按先行后列,升序排序。
v[i]的行列号一定大于等于v[i-1]的行列号,否则返回false。
二分类型:寻找尾端,求最大x,使得Can(x)成立。
参数范围:[0,m+n-2] 整个路径的长度为m+n-1,最多[0,m+n-2]。
返回值:二分返回值+1。

代码

核心代码

#include <iostream>
#include <sstream>
#include <vector>
#include<map>
#include<unordered_map>
#include<set>
#include<unordered_set>
#include<string>
#include<algorithm>
#include<functional>
#include<queue>
#include <stack>
#include<iomanip>
#include<numeric>
#include <math.h>
#include <climits>
#include<assert.h>
#include<cstring>#include <bitset>
using namespace std;template<class T = int>
vector<T> Read(int n,const char* pFormat = "%d") {vector<T> ret(n);for(int i=0;i<n;i++) {scanf(pFormat, &ret[i]);	}return ret;
}template<class T = int>
vector<T> Read( const char* pFormat = "%d") {int n;scanf("%d", &n);vector<T> ret;T d;while (n--) {scanf(pFormat, &d);ret.emplace_back(d);}return ret;
}string ReadChar(int n) {string str;char ch;while (n--) {do{scanf("%c", &ch);} while (('\n' == ch));str += ch;}return str;
}
template<class T1,class T2>
void ReadTo(pair<T1, T2>& pr) {cin >> pr.first >> pr.second;
}template<class INDEX_TYPE>
class CBinarySearch
{
public:CBinarySearch(INDEX_TYPE iMinIndex, INDEX_TYPE iMaxIndex) :m_iMin(iMinIndex), m_iMax(iMaxIndex) {}template<class _Pr>INDEX_TYPE FindFrist(_Pr pr){auto left = m_iMin - 1;auto rightInclue = m_iMax;while (rightInclue - left > 1){const auto mid = left + (rightInclue - left) / 2;if (pr(mid)){rightInclue = mid;}else{left = mid;}}return rightInclue;}template<class _Pr>INDEX_TYPE FindEnd(_Pr pr){INDEX_TYPE leftInclude = m_iMin;INDEX_TYPE right = m_iMax + 1;while (right - leftInclude > 1){const auto mid = leftInclude + (right - leftInclude) / 2;if (pr(mid)){leftInclude = mid;}else{right = mid;}}return leftInclude;}
protected:const INDEX_TYPE m_iMin, m_iMax;
};class Solution {
public:int Ans(vector<vector<int>>& mat) {const int R = mat.size(), C = mat[0].size();const int len = R + C - 1;vector<pair<int, int>> v(len);for (int r = 0; r < R; r++)for (int c = 0; c < C; c++) {if (mat[r][c] < len){v[mat[r][c]] = make_pair(r, c);}}auto Cnt = [&](int x) {vector<pair<int, int>> tmp(v.begin(), v.begin() + x + 1);sort(tmp.begin(), tmp.end());for (int i = 1; i < tmp.size(); i++) {if ((tmp[i].first < tmp[i - 1].first) || (tmp[i].second < tmp[i - 1].second)) { return false; }}return true;};return CBinarySearch<int>(0, len - 1).FindEnd(Cnt) + 1;}
};int main() {
#ifdef _DEBUGfreopen("a.in", "r", stdin);
#endif // DEBUGint T;	cin >> T;for (int i = 0; i < T; i++){int R, C;cin >> R >> C;vector<vector<int>> mat(R);for (int r = 0; r < R; r++) { mat[r] = Read<int>(C); }
#ifdef _DEBUG			//Out(mat, "mat=");#endif	auto res = Solution().Ans(mat);cout << res << std::endl;}return 0;
}

单元测试

vector<vector<int>> mat;TEST_METHOD(TestMethod11){mat = { {1,2,4},{3,0,5} }	;auto res = Solution().Ans(mat);AssertEx(3, res);}TEST_METHOD(TestMethod12){mat = { {1,3,0,4,2} };auto res = Solution().Ans(mat);AssertEx(5, res);}	

扩展阅读

我想对大家说的话
工作中遇到的问题,可以按类别查阅鄙人的算法文章,请点击《算法与数据汇总》。
学习算法:按章节学习《喜缺全书算法册》,大量的题目和测试用例,打包下载。重视操作
有效学习:明确的目标 及时的反馈 拉伸区(难度合适) 专注
闻缺陷则喜(喜缺)是一个美好的愿望,早发现问题,早修改问题,给老板节约钱。
子墨子言之:事无终始,无务多业。也就是我们常说的专业的人做专业的事。
如果程序是一条龙,那算法就是他的是睛
失败+反思=成功 成功+反思=成功

视频课程

先学简单的课程,请移步CSDN学院,听白银讲师(也就是鄙人)的讲解。
https://edu.csdn.net/course/detail/38771
如何你想快速形成战斗了,为老板分忧,请学习C#入职培训、C++入职培训等课程
https://edu.csdn.net/lecturer/6176

测试环境

操作系统:win7 开发环境: VS2019 C++17
或者 操作系统:win10 开发环境: VS2022 C++17
如无特殊说明,本算法用**C++**实现。

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

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

相关文章

springboot015基于SpringBoot的在线视频教育平台的设计与实现(源码+数据库+文档)

源码地址&#xff1a;基于SpringBoot的在线视频教育平台的设计与实现 文章目录 1.项目简介2.部分数据库结构与测试用例3.系统功能结构4.包含的文件列表&#xff08;含论文&#xff09;前端运行截图后端运行截图 1.项目简介 ​ 随着科学技术的飞速发展&#xff0c;各行各业都在…

《深度剖析:生成对抗网络中生成器与判别器的高效协作之道》

在人工智能的前沿领域&#xff0c;生成对抗网络&#xff08;GAN&#xff09;以其独特的对抗学习机制&#xff0c;为数据生成和处理带来了革命性的变革。生成器与判别器作为GAN的核心组件&#xff0c;它们之间的协作效率直接决定了GAN在图像生成、数据增强、风格迁移等众多应用中…

学习Flask:[特殊字符] Day 3:数据库集成

学习目标&#xff1a;使用SQLAlchemy操作数据库 from flask_sqlalchemy import SQLAlchemyapp.config[SQLALCHEMY_DATABASE_URI] sqlite:///site.db db SQLAlchemy(app)class User(db.Model):id db.Column(db.Integer, primary_keyTrue)username db.Column(db.String(20),…

可以免费无限次下载PPT的网站

前言 最近发现了一个超实用的网站&#xff0c;想分享给大家。 在学习和工作的过程中&#xff0c;想必做PPT是一件让大家都很头疼的一件事。 想下载一些PPT模板减少做PPT的工作量&#xff0c;但网上大多精美的PPT都是需要付费才能下载使用。 即使免费也有次数限制&#xff0…

什么是 Java 中的线程安全?

回答 Java 中的线程安全&#xff08;Thread Safety&#xff09;指的是在多线程环境下&#xff0c;当多个线程同时访问和操作共享资源&#xff08;如对象、变量、数据结构等&#xff09;时&#xff0c;能够保证程序的正确性&#xff0c;不会出现数据不一致、竞争条件&#xff0…

建筑三维设计软件如何实现弯道超车?

三个问题 建筑三维设计软件属于工业设计软件的一种&#xff0c;在这个领域一直是国外公司垄断。前些年&#xff0c;在房地产高歌猛进的时代&#xff0c;很多公司也尝试投入到建筑三维设计软件的研发。随着房地产市场行业的下行&#xff0c;建筑三维设计软件的发展也受到了影响…

Android OpenGLES2.0开发(十一):渲染YUV

人生如逆旅&#xff0c;我亦是行人 Android OpenGLES开发&#xff1a;EGL环境搭建Android OpenGLES2.0开发&#xff08;一&#xff09;&#xff1a;艰难的开始Android OpenGLES2.0开发&#xff08;二&#xff09;&#xff1a;环境搭建Android OpenGLES2.0开发&#xff08;三&am…

深入miniqmt:创建交易对象的完整指南

深入miniqmt&#xff1a;创建交易对象的完整指南 在量化交易领域&#xff0c;miniqmt作为一个强大的工具&#xff0c;为开发者提供了执行程序化交易的接口。在进行任何交易操作之前&#xff0c;首先需要创建一个交易对象。本文将详细介绍如何在miniqmt中创建并配置交易对象&am…

日语Learn、英语的再认识

背单词这件事感觉到了某个瓶颈了&#xff0c;没有什么新的区域可以发现&#xff0c;变成了一种类似纯粹的机械记忆&#xff0c;感觉英语的规范程度很低&#xff0c;很多词明明可以通过相近的形式变换&#xff0c;达到更好的学习效果&#xff0c;但却做的很麻烦&#xff0c;同一…

内存泄漏指什么?常见的内存泄漏有哪些?

内存泄漏是指程序在运行过程中&#xff0c;由于某些原因导致程序无法释放已经不再使用的内存&#xff0c;使得这部分内存持续被占用&#xff0c;最终可能导致系统可用内存逐渐减少&#xff0c;严重时会影响系统性能甚至导致程序崩溃。&#xff08;内存泄漏是指程序中已经分配的…

文心一言AI创意画

介绍 文心一言是百度推出的新一代知识增强大语言模型&#xff0c;属于文心大模型家族的新成员。‌它能够与人对话互动、回答问题、协助创作&#xff0c;高效便捷地帮助人们获取信息、知识和灵感。‌ 特点 文心一言基于数万亿数据和数千亿知识进行融合学习&#xff0c;采用预训…

洛谷 P8705:[蓝桥杯 2020 省 B1] 填空题之“试题 E :矩阵” ← 卡特兰数

【题目来源】 https://www.luogu.com.cn/problem/P8705 【题目描述】 把 1∼2020 放在 21010 的矩阵里。要求同一行中右边的比左边大&#xff0c;同一列中下边的比上边的大。一共有多少种方案? 答案很大&#xff0c;你只需要给出方案数除以 2020 的余数即可。 【答案提交】 …

我是如何从 0 到 1 找到 Web3 工作的?

作者&#xff1a;Lotus的人生实验 关于我花了一个月的时间&#xff0c;从 0 到 1 学习 Web3 相关的知识和编程知识。然后找到了一个 Web3 创业公司实习的远程工作。 &#x1f447;&#x1f447;&#x1f447; 我的背景: 计算机科班&#xff0c;学历还可以(大厂门槛水平) 毕业工…

量子网络:构建与应用前景的展望

大家好,我是Echo_Wish,今天我们来探讨一个极具前瞻性的领域——量子网络的构建与应用前景。随着量子计算的发展,量子网络作为量子信息科学的重要组成部分,正在引起越来越多的关注。本文将深入解析量子网络的构建原理,并展望其应用前景。 量子网络的基本概念 量子网络是指…

数据库二三事(8)

高级数据查询 top词语法格式&#xff1a;TOP n &#xff08;percent&#xff09;&#xff08;with ties&#xff09; 查询前n&#xff08;%&#xff09;行数据&#xff0c;&#xff08;包括最后一行取值并列&#xff09; 搭配 order by case&#xff1a; CASE &#xff08;…

linux中conda3安装

1、下载安装包 清华源-》https://mirrors.tuna.tsinghua.edu.cn/# 本文使用Anaconda3-2022.10&#xff0c;对应的下载路径-》https://mirrors.tuna.tsinghua.edu.cn/anaconda/archive/Anaconda3-2022.10-Linux-x86_64.sh 2、将下载到的sh脚本放在Linux中用sh脚本解析器执行 …

2025最新智能优化算法:人工旅鼠算法(Artificial Lemming Algorithm, ALA)求解23个经典函数测试集,MATLAB

一、人工旅鼠优化算法 人工旅鼠算法&#xff08;Artificial Lemming Algorithm, ALA&#xff09;是2025年提出的一种新型生物启发式优化算法&#xff0c;受旅鼠的四种典型行为启发&#xff1a;长距离迁徙、挖洞、觅食和躲避捕食者。该算法通过模拟这些行为来解决复杂的优化问题…

Python游戏编程之赛车游戏6-2

3.2 move()方法的定义 Player类的move()方法用于玩家控制汽车左右移动&#xff0c;当玩家点击键盘上的左右按键时&#xff0c;汽车会相应地进行左右移动。 move()方法的代码如图7所示。 图7 move()方法的代码 其中&#xff0c;第20行代码通过pygame.key.get_pressed()函数获…

日语学习-日语知识点小记-构建基础-JLPT-N4N5阶段(12):普通(ふつう)形 :变化方式 :日常朋友家人之间对话

日语学习-日语知识点小记-构建基础-JLPT-N4&N5阶段(12):普通(ふつう)形 :变化方式 :日常朋友&家人之间对话  1、前言(1)情况说明(2)工程师的信仰2、知识点(1)普通(ふつう)形:Plain style:简体3、单词(1)日语单词(2)日语片假名单词4、相近词辨…

华为hcia——Datacom实验指南——二层交换原理

实验配置 eNSP 什么是二层交换 二层交换是指在同一个ip网段内&#xff0c;数据通过二层交换机进行转发。 什么是mac地址 mac地址也叫做硬件地址&#xff0c;是以太网协议的链路层地址。简单的来说&#xff0c;mac地址就是我们硬件的身份证&#xff0c;独一无二。它是由48个bi…