社交距离 - 华为OD统一考试(C卷)
OD统一考试(C卷)
分值: 200分
题解: Java / Python / C++
题目描述
疫情期间,需要大家保证一定的社交距离,公司组织开交流会议,座位有一排共N个座位,编号分别为[0..N-1],要求员工一个接着一个进入会议室,并且可以在任何时候离开会议室。
满足:每当一个员工进入时,需要坐到最大社交距离的座位(例如:位置A与左右有员工落座的位置距离分别为2和2,位置B与左右有员工落座的位置距离分别为2和3,影响因素都为2个位置,则认为座位A和B与左右位置的社交距离是一样的),如果有多个这样的座位,则坐到索引最小的那个座位。
输入描述
会议室座位总数seatNum,(1 <= seatNum <= 500) 员工的进出顺序 seatOrLeave数组,元素值为1: 表示进场,元素值为负数,表示出场(特殊:位置0的员工不会离开)。
例如-4表示坐在位置4的员工离开 (保证有员工坐在该座位上)。
输出描述
最后进来员工,他会坐在第几个位置,如果位置已满,则输出-1。
示例1
输入:
10
[1, 1, 1, 1, -4, 1]
输出:
5
说明:
seat ->0,坐在任何位置都行,但是要给他安排索引最小的位置,也就是座位0。
seat ->9, 要和旁边的人距离最远,也就是座位9。
seat ->4,位置4与0和9的距离为(4和5),位置5与0和9的距离(5和4),所以位置4和5都是可以选择的座位,按照要求需索引最小的那个座位,也就是座位4。
seat ->2,位置2与0和4的距离为(2和2),位置6与4和9的距离(2和3),位置7与4和9的距离(3和2),影响因素都为2个位置,按照要求需索引最小的那个座位,也就是座位2。leave(4),4号座位的员工离开。
seat-> 5,员工最后坐在5号座位上。
此题为非ACM模式,只需要实现 conferenceSeatDistance 方法即可。
题解
这是一个模拟会议室座位安排的问题,需要根据特定规则安排员工的座位。
- 使用有序 Set 来维护已经被坐的座位情况(java 代码使用 TreeSet )。并通过插入两个虚拟的座位作为边界来方便计算最大社交距离的座位。
- 进入会议室的算法: 使用
join
方法来计算员工进入会议室时的最佳座位。通过遍历 TreeSet 中相邻的位置,计算中间座位的社交距离,找到最大距离的座位,并插入到 TreeSet 中。- 座位计算: 在主方法中,遍历员工的进出顺序,根据不同情况调用
join
方法或者从TreeSet中移除座位。- 输出: 输出最后一个员工坐的位置。
Java
import java.util.Iterator;
import java.util.Scanner;
import java.util.TreeSet;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int seatNum = sc.nextInt();
sc.nextLine();
String seatOrLeaveLine = sc.nextLine();
String[] c = seatOrLeaveLine.substring(1, seatOrLeaveLine.length() - 1).split(", ");
int[] seatOrLeave = new int[c.length];
for (int i = 0; i < c.length; i++) {
seatOrLeave[i] = Integer.parseInt(c[i]);
}
Main socialDistance = new Main();
int ans = socialDistance.conferenceSeatDistance(seatNum, seatOrLeave);
System.out.println(ans);
}
/**
* 计算最后进来的人,坐的位置
*
* @param seatNum 会议室座位总数
* @param seatOrLeave 员工的进出顺序
* @return 最后进来的人,坐的位置
*/
public int conferenceSeatDistance(int seatNum, int[] seatOrLeave) {
TreeSet<Integer> seatTree = new TreeSet<>();
// 插入两个虚拟的座位,有了这两个个边界方便计算最大社交距离的座位
seatTree.add(-2 * (seatNum - 1));
seatTree.add(2 * (seatNum - 1));
int last = -1;
for (int t : seatOrLeave) {
if (t == 1) { // 进来
last = join(seatTree, seatNum);
} else { //
剩余60%内容,订阅专栏后可继续查看/也可单篇购买
2024华为OD机试真题题解 文章被收录于专栏
华为OD机考(C卷、D卷)算法题库(绝对都是原题),帮助你上岸华为(已经不少小伙伴成功上岸)。提供Java、Python、C++ 三种语言的解法。每篇文章都有详细的解题步骤、代码注释详细及相关知识点的练习题。有问题,随时解答