数组不相邻元素之和的最大值

本文讨论了一道面试题目,涉及计算数组中不相邻元素之和的最大值。题目描述来源于LeetCode,模拟了专业窃贼打劫房屋的情况,避免相邻房屋在同一晚被打劫。文章提供了问题分析及优化后的O(1)空间复杂度解决方案。

数组不相邻元素之和的最大值

一、题目描述

今天下午面试老虎证券,被问到这题,当时脑子有点蒙,代码没写出来。这题的意思就是给你一个数组,让你计算元素的和,但是这些元素都不能相邻,求最大的和。其实这题很常见,在leetcode上面也有,但是原题是这样的:

假设你是一个专业的窃贼,准备沿着一条街打劫房屋。每个房子都存放着特定金额的钱。你面临的唯一约束条件是:相邻的房子装着相互联系的防盗系统,且 当相邻的两个房子同一天被打劫时,该系统会自动报警。给定一个非负整数列表,表示每个房子中存放的钱, 算一算,如果今晚去打劫,你最多可以得到多少钱 在不触动报警装置的情况下。

例如:
数组arr为[1, 3, 5, 4, 9],那么结果为 1 + 5 + 9 = 15,再例如数组arr为[5, 1, 3, 11, 7],那么结果为5 + 11 = 16,从这两个例子可以看出,单纯的计算奇数位的和或者偶数位的和得到的结果未必是最大的。
解题思路
定义一个数组p,p[i] 代表从第0到第i个房屋,打劫第i个房屋为止所获得金钱总额,也
### 如何比较数组中相邻两个元素并求最大值 对于给定的任务,即在一个整数数组 `nums` 中寻找 `(nums[i]-1)*(nums[j]-1)` 的最大值,其中 `i != j`,可以通过先对数组进行排序来简化问题。然而,直接按照题目要求计算相邻元素的最大乘积,则不需要完全依赖于排序方法。 #### 方法一:暴力解法 可以直接遍历整个数组两次,找出所有可能的组合,并记录最大的乘积结果。这种方法的时间复杂度较高,为 O(n^2),但对于理解基本逻辑很有帮助。 ```java public int maxProduct(int[] nums) { int n = nums.length; int result = Integer.MIN_VALUE; for (int i = 0; i < n - 1; ++i){ for (int j = i + 1; j < n; ++j){ result = Math.max(result, (nums[i] - 1) * (nums[j] - 1)); } } return result; } ``` #### 方法二:优化后的线性扫描算法 考虑到只需要找到两个不同的位置使得它们减去1之后相乘的结果最大化,实际上只需关注数组中的前两大数值即可。因此,在一次遍历过程中维护当前遇到过的最大值和次大值,最后根据这两个值得到最终答案。此方案时间复杂度降到了O(n)[^1]。 ```java public int optimizedMaxProduct(int[] nums) { int firstLargest = 0, secondLargest = 0; for (final int num : nums) { if (num > firstLargest) { // 更新最大值与第二大值 secondLargest = firstLargest; firstLargest = num; } else if (num > secondLargest && num != firstLargest){ // 确保不重复选取相同元素 secondLargest = num; } } return (firstLargest - 1); } ``` 上述两种方式都能有效地解决这个问题,但是推荐使用第二种更高效的解决方案。它不仅减少了不必要的循环次数,而且更容易理解和实现。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值