[Swift]LeetCode1187. 使数组严格递增 | Make Array Strictly Increasing
★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★
➤微信公众号:山青咏芝(shanqingyongzhi)
➤博客园地址:山青咏芝(www.zengqiang.org)
➤GitHub地址:https://github.com/strengthen/LeetCode
➤原文地址:https://www.cnblogs.com/strengthen/p/11484999.html
➤如果链接不是山青咏芝的博客园地址,则可能是爬取作者的文章。
➤原文已修改更新!强烈建议点击原文地址阅读!支持作者!支持原创!
★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★
Given two integer arrays arr1
and arr2
, return the minimum number of operations (possibly zero) needed to make arr1
strictly increasing.
In one operation, you can choose two indices 0 <= i < arr1.length
and 0 <= j < arr2.length
and do the assignment arr1[i] = arr2[j]
.
If there is no way to make arr1
strictly increasing, return -1
.
Example 1:
Input: arr1 = [1,5,3,6,7], arr2 = [1,3,2,4] Output: 1 Explanation: Replace5
with2
, thenarr1 = [1, 2, 3, 6, 7]
.
Example 2:
Input: arr1 = [1,5,3,6,7], arr2 = [4,3,1] Output: 2 Explanation: Replace5
with3
and then replace3
with4
.arr1 = [1, 3, 4, 6, 7]
.
Example 3:
Input: arr1 = [1,5,3,6,7], arr2 = [1,6,3,3]
Output: -1
Explanation: You can't make arr1
strictly increasing.
Constraints:
1 <= arr1.length, arr2.length <= 2000
0 <= arr1[i], arr2[i] <= 10^9
给你两个整数数组 arr1
和 arr2
,返回使 arr1
严格递增所需要的最小「操作」数(可能为 0)。
每一步「操作」中,你可以分别从 arr1
和 arr2
中各选出一个索引,分别为 i
和 j
,0 <= i < arr1.length
和 0 <= j < arr2.length
,然后进行赋值运算 arr1[i] = arr2[j]
。
如果无法让 arr1
严格递增,请返回 -1
。
示例 1:
输入:arr1 = [1,5,3,6,7], arr2 = [1,3,2,4] 输出:1 解释:用 2 来替换5,之后
arr1 = [1, 2, 3, 6, 7]
。
示例 2:
输入:arr1 = [1,5,3,6,7], arr2 = [4,3,1] 输出:2 解释:用 3 来替换5,然后
用 4 来替换 3,得到
arr1 = [1, 3, 4, 6, 7]
。
示例 3:
输入:arr1 = [1,5,3,6,7], arr2 = [1,6,3,3]
输出:-1
解释:无法使 arr1 严格递增
。
提示:
1 <= arr1.length, arr2.length <= 2000
0 <= arr1[i], arr2[i] <= 10^9
Runtime: 644 ms
1 class Solution { 2 func makeArrayIncreasing(_ arr1: [Int], _ arr2: [Int]) -> Int { 3 let len1:Int = arr1.count 4 var arr2 = arr2.sorted(by:<) 5 arr2.append(-1) 6 var ar:[Int] = [Int]() 7 for i in 0..<(arr2.count - 1) 8 { 9 if arr2[i] != arr2[i + 1] 10 { 11 ar.append(arr2[i]) 12 } 13 } 14 arr2 = ar 15 let len2:Int = arr2.count 16 var f:[[Int]] = [[Int]](repeating:[Int](repeating:0,count:2002),count:2002) 17 for i in 0..<len1 18 { 19 for j in 0...len2 20 { 21 f[i][j] = 10000000 22 f[i][j] = 10000000 23 } 24 } 25 for j in 0...len2 26 { 27 f[0][j] = 1 28 } 29 f[0][0] = 0 30 for i in 1..<len1 31 { 32 if arr1[i] > arr1[i - 1] 33 { 34 f[i][0] = min(f[i][0], f[i - 1][0]) 35 } 36 var l:Int = 0 37 var r:Int = len2 - 1 38 var ind:Int = -1 39 while(l <= r) 40 { 41 var mid:Int = (l + r) / 2 42 if arr2[mid] < arr1[i] 43 { 44 l = mid + 1 45 ind = mid 46 } 47 else 48 { 49 r = mid - 1 50 } 51 } 52 if ind != -1 53 { 54 f[i][0] = min(f[i][0], f[i - 1][ind + 1]) 55 } 56 for j in 1...len2 57 { 58 if arr2[j - 1] > arr1[i - 1] 59 { 60 f[i][j] = min(f[i][j], f[i - 1][0] + 1) 61 } 62 if j > 1 63 { 64 f[i][j] = min(f[i][j], f[i - 1][j - 1] + 1) 65 } 66 } 67 } 68 var ans:Int = f[len1 - 1][0]; 69 for j in 1...len2 70 { 71 ans = min(ans, f[len1 - 1][j]) 72 } 73 return ans == 10000000 ? -1 : ans 74 } 75 }
696ms
1 class Solution { 2 func makeArrayIncreasing(_ arr1: [Int], _ arr2: [Int]) -> Int { 3 var hash = [Key:Int]() 4 let result = _makeArrayIncreasing(arr1, Array(Set(arr2)).sorted(), 0, Int.min, &hash) 5 return result != Int.max ? result : -1 6 } 7 8 func _makeArrayIncreasing(_ arr1: [Int], 9 _ arr2: [Int], 10 _ index: Int, 11 _ currMin: Int, 12 _ hash: inout [Key:Int]) -> Int { 13 guard index < arr1.count else { return 0 } 14 15 let key = Key(index,currMin) 16 if let cached = hash[key] { return cached } 17 18 let keepValue = arr1[index] > currMin ? _makeArrayIncreasing(arr1,arr2,index+1,arr1[index],&hash) : Int.max 19 20 let swapValue: Int 21 let swapIndex = bSearch(arr2, 0, arr2.count-1, currMin) 22 23 if swapIndex != -1 { 24 let swapRecursion = _makeArrayIncreasing(arr1,arr2,index+1,arr2[swapIndex],&hash) 25 if swapRecursion != Int.max { 26 swapValue = 1 + swapRecursion 27 } else { 28 swapValue = Int.max 29 } 30 } else { 31 swapValue = Int.max 32 } 33 34 let result = keepValue == Int.max && swapValue == Int.max ? Int.max : min(keepValue, swapValue) 35 hash[key] = result 36 return result 37 } 38 39 func bSearch(_ array: [Int], _ min: Int, _ max: Int, _ value: Int) -> Int { 40 guard min <= max else { return -1 } 41 42 let index = min + (max - min) / 2 43 44 if array[index] <= value { 45 return bSearch(array,index+1,max,value) 46 } 47 else { // array[index] > value 48 if index > 0, array[index-1] > value { 49 return bSearch(array,min,index-1,value) 50 } 51 return index 52 } 53 54 } 55 } 56 57 struct Key: Hashable { 58 let index: Int 59 let currMin: Int 60 61 init(_ index: Int, _ currMin: Int) { 62 self.index = index 63 self.currMin = currMin 64 } 65 }
712ms
1 class Solution { 2 func makeArrayIncreasing(_ arr1: [Int], _ arr2: [Int]) -> Int { 3 let n1 = arr1.count 4 let s2 = Set<Int>(arr2) 5 var a3 = Array(s2) 6 a3 = a3.sorted() 7 let n3 = a3.count 8 9 var dp = [[Int]](repeating: [Int](repeating: Int.max/2, count: n3), count: n1) 10 var dp1 = [Int](repeating: Int.max/2, count: n1) 11 for i in 0..<n3 { 12 dp[0][i] = (arr1[0] != a3[i] ? 1 : 0) 13 } 14 dp1[0] = 0 15 16 for i in 1..<n1 { 17 var cur = dp[i-1][0] 18 for j in 1..<n3 { 19 dp[i][j] = min(dp[i][j], cur + (arr1[i] != a3[j] ? 1 : 0)) 20 cur = min(cur, dp[i-1][j]) 21 } 22 23 for j in 0..<n3 { 24 if a3[j] > arr1[i-1] { 25 dp[i][j] = min(dp[i][j], dp1[i-1] + (arr1[i] != a3[j] ? 1 : 0)) 26 } 27 } 28 29 for j in 0..<n3 { 30 if a3[j] < arr1[i] { 31 dp1[i] = min(dp1[i], dp[i - 1][j]) 32 } 33 } 34 35 if arr1[i - 1] < arr1[i] { 36 dp1[i] = min(dp1[i], dp1[i - 1]) 37 } 38 39 } 40 41 var res = Int.max/2 42 for i in 0..<n3 { 43 if dp[n1-1][i] >= 0 { 44 res = min(res, dp[n1-1][i]) 45 } 46 } 47 if dp1[n1 - 1] >= 0 { 48 res = min(res, dp1[n1 - 1]) 49 } 50 return res >= Int.max/2 ? -1 : res 51 } 52 }