算法沉淀第二天(Catching the Krug)

目录

引言:

[Catching the Krug](#Catching the Krug)

题意分析

逻辑梳理

代码实现

结语:


引言:

今天是算法沉淀的第二天,开的是CF评级为1300的一道题,这道题用分类讨论就可以解决了,甚至不需要用到算法,那么接下来,话不多说,我们就进入今天的算法讲解--------------------->

​​​​​​​


Catching the Krug

按照惯例,我们先来看题目

题意分析

题目链接如下Problem - 2152B - Codeforces

不想跳转的可看下图

这道题虽然题目描述的很长,其实目的很简单,就是有俩个人,假设分别是A人和B人,然后,A人负责逃跑,B人负责追击,如果B人追不到A人就输出-1,如果B人如果能追到A人就输出最少的追击次数,A和B在同一个格子上就算追击到了

A不想被B追到,所以A会用最优的方式来躲B,然后B想快点追上A,所以B也会用最优的方式来追击A

然后会问你t种情况,每种情况先告诉你A的坐标再告诉你B的坐标

那A和B的走法是怎么走的呢,A每次可以横着或者竖着走一格(也可以不走),B则是每次可以走的位置是他所在的格子的周围一圈(也可以不走),然后,走法是A先走,再B走,这样轮流走

那么,题目意思讲完了,接下来,就进入逻辑梳理环节咯


逻辑梳理

首先,A只能横着或竖着走,但B可以斜着走,所以如果B想要快点追到A,肯定会堵A的路,A最终肯定会被抓到,所以输出-1的情况是不存在的

那么,既然A已经知道自己会被堵,那么A肯定会移动到最远的位置,然后不动,这样才能躲得更久,那么A可以去上下的边界,也可以去左右的边界,那么具体去哪里也要看A与B的位置关系

那具体怎么移,我们可以通过B来看,不管A怎么移动,因为B的可移动性远高于A,所以可以相当于是B的平推,因为B可以通过斜着走堵住A的未来路,所以这时候就只会有俩种情况了,一种是B沿着水平方向平推到边界,另一种是B沿着竖直方向平推到边界

那么,我们只需要去这俩种情况的最大值就好了,因为A想晚点被抓到,所以B肯定要走更多的操作次数

那么,情况分析完了,接下来,就进行分类讨论就好啦

我们可以通过A,B的x轴坐标的差异,分为三种情况,接着再细分,假设A的坐标为(x1,y1),B的坐标为(x2,y2)

若x1<x2

这时候,A的位置在B的左侧,我们可以对A的位置通过y的差距来进行进一步细分

如果y1>y2

这说明A的位置在B的左上角,A可以往左走,也可以往上走,那B追到A的移动次数就是B到左边界和上边界的俩个值中的较大值

如果y1>y2

这说明A的位置在B的左下角,A可以往左走,也可以往下走,那B追到A的移动次数就是B到左边界和下边界的俩个值中的较大值

如果y1==y2

这说明A的位置在B的正左边,这时候B只要一直往左走就能抓到了,如果A想上下走,B只要斜着往左压过去就可以了,所以这种情况下的移动次数就是B到左边界的移动次数

若x1>x2

这个就跟上面那个同理了,只是算的时候数据会变化

若x1==x2

这个情况就比较特殊了,这个就跟上面x1!=x2时,但y1==y2一样,只需要算出B到对应边界的操作次数就好了

那么所有情况就讨论完了,接下来就进入代码实现的环节啦


代码实现

代码的思路逻辑梳理已经讲的很清楚啦,那么接下来,就直接展示AC码啦

cpp 复制代码
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <string.h>
#include <algorithm>
#include <queue>
using namespace std;

int t;

void solve()
{
	long long n, x1, y1, x2, y2;
	cin >> n >> x1 >> y1 >> x2 >> y2;
	if (x1 < x2)
	{
		if (y1 == y2)
		{
			cout << x2 << endl;
		}
		else if (y1 < y2)
		{
			cout << max(x2, y2) << endl;
		}
		else
		{
			cout << max(x2, n - y2) << endl;
		}
	}
	else if (x1 > x2)
	{
		if (y1 == y2)
		{
			cout << n - x2 << endl;
		}
		else if (y1 < y2)
		{
			cout << max(n - x2, y2) << endl;
		}
		else
		{
			cout << max(n - x2, n - y2) << endl;
		}
	}
	else
	{
		if (y1 < y2)
			cout << y2 << endl;
		else
			cout << n - y2 << endl;
	}
}

int main()
{
	cin >> t;
	while (t--)
	{
		solve();
	}
	return 0;
}

结语:

今日算法讲解到此结束啦,希望对你们有所帮助,谢谢观看,如果觉得不错可以分享给朋友哟。有什么看不懂的可以评论问哦,

相关推荐
renhongxia19 分钟前
如何基于知识图谱进行故障原因、事故原因推理,需要用到哪些算法
人工智能·深度学习·算法·机器学习·自然语言处理·transformer·知识图谱
坚持就完事了10 分钟前
数据结构之树(Java实现)
java·算法
算法备案代理12 分钟前
大模型备案与算法备案,企业该如何选择?
人工智能·算法·大模型·算法备案
赛姐在努力.36 分钟前
【拓扑排序】-- 算法原理讲解,及实现拓扑排序,附赠热门例题
java·算法·图论
rainbow68891 小时前
EffectiveC++入门:四大习惯提升代码质量
c++
秋邱1 小时前
用 Python 写出 C++ 的性能?用CANN中PyPTO 算子开发硬核上手指南
开发语言·c++·python
我在人间贩卖青春2 小时前
C++之析构函数
c++·析构函数
野犬寒鸦2 小时前
从零起步学习并发编程 || 第六章:ReentrantLock与synchronized 的辨析及运用
java·服务器·数据库·后端·学习·算法
霖霖总总2 小时前
[小技巧66]当自增主键耗尽:MySQL 主键溢出问题深度解析与雪花算法替代方案
mysql·算法
rainbow68892 小时前
深入解析C++STL:map与set底层奥秘
java·数据结构·算法