Java 中的情侣牵手问题17 Mar 2025 | 5 分钟阅读 这是一个非常有趣的问题,经常在Google、Amazon、TCS、Accenture等顶级IT公司的面试中出现。通过解决这个问题,可以考察面试者的逻辑能力、批判性思维和解决问题的能力。因此,在本节中,我们将用不同的方法和逻辑来解决Java中的情侣牵手问题。我们还将为此创建Java程序。 ![]() 问题陈述在这个问题中,我们有n对情侣,共2n人坐在2n个座位(排成一排),他们想要牵手。我们需要找到最少需要进行的交换(座位交换)次数,以便每对情侣都能坐在旁边。我们可以选择任意两个人进行交换,他们可以站起来并交换座位。 注意:数组的长度必须是偶数,否则会有一个人无法配对。让我们通过示例来理解。 示例 1输入: couple = [4, 1, 5, 2] 输出 1 解释: 在这里,我们只需要一次交换(1与5)就可以配对,我们得到 [4, 5, 1, 2]。在这里,人的顺序无关紧要。例如,[5, 4, 2, 1] 和 [4, 5, 1, 2] 是相同的。 示例 2输入: couple = [1, 2, 8, 9] 输出 0 解释: 在这里,不需要交换座位,所有情侣已经手拉手了。 问题解决方案为了解决这个问题,我们将定义一个整数数组 row。数组索引表示坐在第 i 个座位上的情侣。人和座位用0到2N-1的整数表示。情侣按顺序编号,第一对是(0, 1),第二对是(2, 3),以此类推,最后一对是(2N-2, 2N-1)。 这些情侣的初始座位 row[i] 由最初坐在第 i 个座位上的人决定。 这个问题可以用多种方法解决,例如使用并查集、贪心算法或排列图的循环分解。让我们逐一详细讨论。 解决方案1:使用排列图和图分解排列图论允许给定一对排列,例如G1:(W, X, W, Y, W, Z, Y) 和 G2:(X, Y, Z, W, W, Y, W)。通过连接G1到G2的边,我们可以用图表示一对排列。根据观察,如果在任何位置[i],我们有G1[i]=G2[i],那么该顶点应该有一个自连接边。 ![]() 为了将G2转换为G1,我们需要进行交换,以便移除两个顶点之间的边。简单来说,就是将顶点变成自连接边。 如果我们观察到图中的任何循环,移除所有非自连接边的最小步骤是边数-1。因此,总交换次数将是∑(Ck-1),其中C1, C2, C3, …. Ck是图中连通分量的长度。 我们还可以通过将图分解为不同的循环来最小化总交换次数,使每个循环尽可能小(因为边的数量是固定的,但我们得到的循环越多,交换次数就减去1的次数越多)。 步骤:首先,确定图中连通部分的数量。为此,我们使用了一个名为 connectedNumber 的变量。 假设所有情侣都坐在一起,在这种情况下,连通部分的数量是row.length/2。 变量connectedNumber将在我们进行右交换以配对一对情侣时增加1。执行交换过程,直到变量connectedNumber等于row.length/2。所以这个问题的答案是row.length/2 - connectedNumber。 CoupleHoldingHands1.java 输出 1 解决方案2:贪心方法如果我们仔细观察图(上面),会发现存在一个贪心的方法。只有一种方法可以将图分解,使得任何有助于匹配至少一对情侣的交换都是一个贪心操作。 在这个方法中,我们使用一个HashMap来计算每个人的位置。然后,再次遍历行。如果我们发现一对不匹配的人,我们就找到他们匹配的对象所在的位置并进行交换。我们持续执行贪心操作并计算交换次数。 CoupleHoldingHands2.java 输出 2 复杂度以上所有方法的时空复杂度均为O(n),其中n是情侣的数量。 下一个主题Java 中计算排序二元数组中的1的数量 |
自然数是指包含从 1 到无穷大的所有正整数的数字。例如,1、2、3、4、5、......、n。当我们把这些数字加在一起时,我们就得到了自然数的和。在本节中,我们将创建以下程序:Java...
阅读 3 分钟
在给定的数组中,任务是找出数组的第 k 小的元素,其中 k 始终小于给定数组的大小。示例:输入:arr[] = {56, 34, 7, 9, 0, 48, 41, 8} k = 3 输出:数组的第 3 小元素...
11 分钟阅读
Java 中有 23 种设计模式,它们为应用程序设计中常见的问题提供了明确的解决方案。它代表了应用程序及其流程的详细描述。它是许多……中可用的问题解决方案。
阅读9分钟
组合设计模式是一种设计模式,它允许我们将对象排列成树形结构来表示部分-整体设计。它允许客户精确地处理单个项目和包。简单来说,它允许我们将单个对象与...
5 分钟阅读
Java 数组转列表 在 Java 编程中,数组和列表是基本的数据结构,通常用于存储元素的集合。虽然数组提供固定大小的存储,但列表提供动态大小调整和其他功能。有时我们可能需要将数组转换为列表以...
阅读 6 分钟
在 Java 中终止应用程序可能看起来是一个简单的挑战,但有多种技术可以优雅地终止给定的程序,或在出现意外问题时强制终止。在本节中,我们将讨论终止 Java 程序的各种方法以及...
阅读 4 分钟
代码覆盖率工具对软件开发至关重要,因为它们可以提供有关测试执行情况的信息。这些工具可以帮助开发人员确定代码的哪些部分已被测试,哪些部分仍需要工作。有许多代码覆盖率...
阅读 3 分钟
在 Java 中,变量是保存值的容器。变量名表示内存位置的名称。每个变量包含三个元素:数据类型、变量名和值。变量可能具有作用域(私有、受保护),但这取决于需求。数据类型:它定义...
阅读 4 分钟
在 Java 中,由 Enumeration 的 Element 方法抛出,表明枚举中没有更多元素了。由以下方法抛出 - Enumeration 接口的 Element() 方法 NamingEnumeration 接口的 () 方法 StringTokenizer 类的 Element() 方法 Iterator 接口的 () 方法 是一个...
阅读 2 分钟
Java 中的 Stream.skip(long n) 方法是 Java 8 中引入的 Stream API 的重要组成部分。它使开发人员能够构建数据操作管道。skip() 方法在跳过数据集中的特定数量的元素时特别有用...
阅读9分钟
我们请求您订阅我们的新闻通讯以获取最新更新。
我们提供所有技术(如 Java 教程、Android、Java 框架)的教程和面试问题
G-13, 2nd Floor, Sec-3, Noida, UP, 201301, India