华为OD机试 - 计算数组中心位置 - 双指针(Java 2024 E卷 100分)

这篇博客介绍了一道华为在线开发者(OD)测试题,涉及计算数组中心位置的问题。通过双指针法,当左右两侧元素乘积相等时找到中心位置。文章提供了详细的解题思路和Java代码实现,并附有输入输出示例。

一、题目描述

给你一个整数数组 nums,请计算数组的中心位置,数组的中心位置是数组的一个下标,其左侧所有元素相乘的积等于右侧所有元素相的积。

数组第一个元素的左侧积为 1,最后一个元素的右侧积为 1。如果数组有多个中心位置,应该返回最靠近左边的那一个,如果数组不存在中心位置,返回-1。

二、输入描述

2 5 3 6 5 6

三、输出描述

3

四、测试用例

测试用例1

1、输入

2 5 3 6 5 6

2、输出

3

3、说明

下标 3 左侧乘积 = 2×5×3 = 30,右侧乘积 = 5×6 = 30,满足条件,是最左的满足条件的中心位置。

测试用例2

1、输入

1 2 3 4

2、输出

-1

3、说明

无论哪个下标,都无法使左右乘积相等,因此返回 -1。

五、解题思路

  1. 读取输入的整数数组 arr;
  2. 获取
### 华为OD题概述 华为OD主要考察候选人的编程能力和算法思维能力[^1]。测通常涉及数据结构、算法设计以及实际问题解决技巧等方面的内容。 #### 题目一:字符串处理 一道常见的题目是关于字符串的操作,例如反转给定的字符串并移除其中所有的非字母字符: ```java public class StringManipulation { public static String reverseAndFilter(String input) { StringBuilder filtered = new StringBuilder(); // 过滤掉非字母字符 for (char c : input.toCharArray()) { if ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z')) { filtered.append(c); } } // 反转过滤后的字符串 return filtered.reverse().toString(); } } ``` 此段代码实现了对输入字符串的预处理功能,先去除所有非字母字符再将其倒序排列。 #### 题目二:数组操作 另一类典型问题是围绕着数组展开的任务,比如寻找两个有序整数列表中的中位数值: ```java public double findMedianSortedArrays(int[] nums1, int[] nums2) { int m = nums1.length; int n = nums2.length; if (m > n) { // Ensure that binary search happens on the smaller array. return findMedianSortedArrays(nums2, nums1); } int iMin = 0, iMax = m; while (iMin <= iMax) { int i = (iMin + iMax) / 2; int j = (m + n + 1) / 2 - i; if (j != 0 && i != m && nums2[j-1] > nums1[i]) { iMin = i + 1; } else if (i != 0 && j != n && nums1[i-1] > nums2[j]) { iMax = i - 1; } else { int maxLeft = 0; if (i == 0) { maxLeft = nums2[j-1]; } else if (j == 0) { maxLeft = nums1[i-1]; } else { maxLeft = Math.max(nums1[i-1], nums2[j-1]); } if ((m + n) % 2 == 1) { return maxLeft; } int minRight = 0; if (i == m) { minRight = nums2[j]; } else if (j == n) { minRight = nums1[i]; } else { minRight = Math.min(nums1[i], nums2[j]); } return (maxLeft + minRight) / 2.0; } } throw new IllegalArgumentException("Input arrays are not sorted."); } ``` 上述实现展示了如何高效地找到两个已经排序好的数组之间的中间值,这是一道经典的面题,在很多场景下都有应用价值。 #### 题目三:链表管理 对于更高级别的挑战,则可能涉及到单向/双向链表节点间的复杂交互逻辑,如删除指定位置处的一个结点: ```java class ListNode { int val; ListNode next; ListNode() {} ListNode(int val) { this.val = val; } ListNode(int val, ListNode next) { this.val = val; this.next = next; } } public void deleteNode(ListNode node) { if(node==null||node.next==null){ return ; } node.val=node.next.val; node.next=node.next.next; } ``` 这段程序片段提供了一种巧妙的方法来绕过直接访问前驱指针的需求,从而简化了解决方案的设计过程。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

哪 吒

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值