Easy

题目描述

给你一个下标从 0 开始的整数数组 nums,其中 nums.length == n,找出 nums[i]nums[j] 之间的 最大差值,其中 0 <= i < j < nnums[i] < nums[j]

返回 最大差值。如果不存在满足要求的 ij,返回 -1

示例 1:

输入:nums = [7,1,5,4]
输出:4
解释:
最大差值出现在 i = 1 且 j = 2 时,nums[j] - nums[i] = 5 - 1 = 4 。
注意,尽管 i = 1 且 j = 0 时,nums[j] - nums[i] = 7 - 1 = 6 > 4 ,但 i > j ,所以不满足题面要求。

示例 2:

输入:nums = [9,4,3,2]
输出:-1
解释:
不存在同时满足 i < j 和 nums[i] < nums[j] 的 i, j 组合。

示例 3:

输入:nums = [1,5,2,10]
输出:9
解释:
最大差值出现在 i = 0 且 j = 3 时,nums[j] - nums[i] = 10 - 1 = 9 。

提示:

  • n == nums.length
  • 2 <= n <= 1000
  • 1 <= nums[i] <= 10^9

解题思路

解题思路

这道题要求找到满足 i < jnums[i] < nums[j] 条件下的最大差值 nums[j] - nums[i]

方法一:暴力枚举(O(n²)) 直接双重循环枚举所有可能的 i 和 j 组合,检查是否满足条件并更新最大差值。

方法二:一次遍历优化(推荐) 关键观察:要使差值 nums[j] - nums[i] 最大,我们需要:

  1. nums[i] 尽可能小
  2. nums[j] 尽可能大(且位置在 nums[i] 之后)

算法思路:

  • 从左到右遍历数组,维护到目前为止遇到的最小值
  • 对于每个位置 j,计算 nums[j] - min_val 的差值
  • 只有当 nums[j] > min_val 时,这个差值才是有效的
  • 不断更新最大差值

这样只需要一次遍历就能找到答案,时间复杂度降到 O(n)。

特殊情况处理:如果整个数组是严格递减的,那么不存在满足条件的 i 和 j,返回 -1。

代码实现

class Solution {
public:
    int maximumDifference(vector<int>& nums) {
        int maxDiff = -1;
        int minVal = nums[0];
        
        for (int j = 1; j < nums.size(); j++) {
            if (nums[j] > minVal) {
                maxDiff = max(maxDiff, nums[j] - minVal);
            }
            minVal = min(minVal, nums[j]);
        }
        
        return maxDiff;
    }
};
class Solution:
    def maximumDifference(self, nums: List[int]) -> int:
        max_diff = -1
        min_val = nums[0]
        
        for j in range(1, len(nums)):
            if nums[j] > min_val:
                max_diff = max(max_diff, nums[j] - min_val)
            min_val = min(min_val, nums[j])
        
        return max_diff
public class Solution {
    public int MaximumDifference(int[] nums) {
        int maxDiff = -1;
        int minVal = nums[0];
        
        for (int j = 1; j < nums.Length; j++) {
            if (nums[j] > minVal) {
                maxDiff = Math.Max(maxDiff, nums[j] - minVal);
            }
            minVal = Math.Min(minVal, nums[j]);
        }
        
        return maxDiff;
    }
}
var maximumDifference = function(nums) {
    let maxDiff = -1;
    let minVal = nums[0];
    
    for (let j = 1; j < nums.length; j++) {
        if (nums[j] > minVal) {
            maxDiff = Math.max(maxDiff, nums[j] - minVal);
        }
        minVal = Math.min(minVal, nums[j]);
    }
    
    return maxDiff;
};

复杂度分析

解法时间复杂度空间复杂度
一次遍历O(n)O(1)
暴力枚举O(n²)O(1)

推荐解法:一次遍历

  • 时间复杂度:O(n),只需要遍历数组一次
  • 空间复杂度:O(1),只使用了常数级别的额外空间

相关题目