引言
现在算法题中,有时会遇到求解绝对值最值的问题,比如给定一个数组,求解 a b s ∣ a i − a j ∣ abs|a_i - a_j| abs∣ai−aj∣的最大值。诸如此类问题,暴力解法是用 O ( n 2 ) O(n^2) O(n2)时间复杂度遍历 i , j i,j i,j。而一种常用优化是将绝对值拆开,比如 a b s ∣ a i − a j ∣ = m a x ( a i − a j , a j − a i ) abs|a_i - a_j| = max(a_i - a_j, a_j - a_i) abs∣ai−aj∣=max(ai−aj,aj−ai),将问题拆成两个子问题,而每个子问题通过维护当前最小值,即 O ( n ) O(n) O(n)的时间可解出。最后通过 O ( 1 ) O(1) O(1)取二者最值即可。
下面分享三道利用此技巧解题的算法题,难度按升序排列。
Leetcode 1131
题意:
给定两个数组 a r r 1 arr1 arr1和 a r r 2 arr2 arr2,让找两个下标 i i i和 j j j,使得 ∣ a r r 1 [ i ] − a r r 1 [ j ] ∣ + ∣ a r r 2 [ i ] − a r r 2 [ j ] ∣ + ∣ i − j ∣ |arr1[i] - arr1[j]| + |arr2[i] - arr2[j]| + |i - j| ∣arr1[i]−arr1[j]∣+∣arr2[i]−arr2[j]∣+∣i−j∣最大。
思路:
这里直接拆开三个绝对值,得到以下8个子问题:
然后我们把有关于下标 i i i和下标 j j j的项提出来放在一起,发现其实子问题只有以下四个:1&8;2&7;3&6;4&5(比如1和8,它们只不过把两个下标 i i i和