局部峰值指比相邻元素都大的数组元素;边界元素只需大于唯一邻居,单元素数组自身即为局部峰值;线性扫描时间复杂度o(n),二分查找在山峰型数组中可达o(log n)。

局部峰值(Local Peak)指数组中某个元素,它比其相邻元素都大。对于一维数组,位置 i 是局部峰值当且仅当:arr[i] > arr[i-1] 且 arr[i] > arr[i+1](边界元素只需大于唯一邻居即可)。
边界情况要单独处理
数组首尾元素只有一个邻居,判断逻辑不同:
- 索引 0 是局部峰值 ⇔
arr[0] > arr[1](前提是数组长度 ≥ 2) - 索引 n−1 是局部峰值 ⇔
arr[n−1] > arr[n−2] - 单元素数组:该元素本身就是局部峰值
线性扫描是最直观解法
遍历每个位置,按定义逐个比较。时间复杂度 O(n),空间 O(1),适合大多数场景:
$arr = [1, 3, 2, 4, 1];
$peaks = [];
<p>$n = count($arr);
for ($i = 0; $i < $n; $i++) {
$isPeak = false;
if ($n === 1) {
$isPeak = true;
} elseif ($i === 0) {
$isPeak = $arr[0] > $arr[1];
} elseif ($i === $n - 1) {
$isPeak = $arr[$i] > $arr[$i - 1];
} else {
$isPeak = $arr[$i] > $arr[$i - 1] && $arr[$i] > $arr[$i + 1];
}
if ($isPeak) {
$peaks[] = $arr[$i];
}
}
// $peaks = [3, 4]
二分查找适用于“先增后减”类数组
若题目保证数组存在局部峰值且满足“山峰型”结构(如单调递增到某点再单调递减),可用二分在 O(log n) 时间内找一个局部峰值:
立即学习“PHP免费学习笔记(深入)”;
- 比较中点
mid与其右邻mid+1 - 若
arr[mid] ,说明右侧还在上升,峰值在右半段 - 否则峰值在左半段(含 mid)
- 注意:此方法只保证找到一个局部峰值,不保证找全
返回全部还是任一?看题目要求
实际使用前明确需求:
- 求所有局部峰值 → 用线性扫描,完整遍历
- 只要任意一个局部峰值 → 可选二分(需满足前提)或直接返回首个符合条件的值
- 注意重复值:严格大于邻居才算,等于不算(除非题目允许 ≥)











