为有牺牲多壮志,敢教日月换新天。

[Swift]LeetCode40. 组合总和 II | Combination Sum II

★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★
➤微信公众号:山青咏芝(shanqingyongzhi)
➤博客园地址:山青咏芝(https://www.cnblogs.com/strengthen/
➤GitHub地址:https://github.com/strengthen/LeetCode
➤原文地址:https://www.cnblogs.com/strengthen/p/9901355.html 
➤如果链接不是山青咏芝的博客园地址,则可能是爬取作者的文章。
➤原文已修改更新!强烈建议点击原文地址阅读!支持作者!支持原创!
★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★

热烈欢迎,请直接点击!!!

进入博主App Store主页,下载使用各个作品!!!

注:博主将坚持每月上线一个新app!!!

Given a collection of candidate numbers (candidates) and a target number (target), find all unique combinations in candidates where the candidate numbers sums to target.

Each number in candidates may only be used once in the combination.

Note:

  • All numbers (including target) will be positive integers.
  • The solution set must not contain duplicate combinations.

Example 1:

Input: candidates = [10,1,2,7,6,1,5], target = 8,
A solution set is:
[
  [1, 7],
  [1, 2, 5],
  [2, 6],
  [1, 1, 6]
]

Example 2:

Input: candidates = [2,5,2,1,2], target = 5,
A solution set is:
[
  [1,2,2],
  [5]
]


给定一个数组 candidates 和一个目标数 target ,找出 candidates 中所有可以使数字和为 target 的组合。

candidates 中的每个数字在每个组合中只能使用一次。

说明:

  • 所有数字(包括目标数)都是正整数。
  • 解集不能包含重复的组合。 

示例 1:

输入: candidates = [10,1,2,7,6,1,5], target = 8,
所求解集为:
[
  [1, 7],
  [1, 2, 5],
  [2, 6],
  [1, 1, 6]
]

示例 2:

输入: candidates = [2,5,2,1,2], target = 5,
所求解集为:
[
  [1,2,2],
  [5]
]

16ma
 1 class Solution {
 2     var result = [[Int]]()
 3     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 4         var tempCandidates = candidates
 5         tempCandidates.sort{$0<$1}
 6         combinationSum(tempCandidates, target, 0, [Int]())
 7         return result
 8     }
 9     
10     func combinationSum(_ candidates: [Int], _ target: Int, _ currentInex: Int, _ usdedNums: [Int]) {
11         if target <= 0  {
12             if target == 0 {
13                 result.append(usdedNums)                     
14             }
15             return
16         }
17         
18         var previousNum = 0
19         for i in currentInex..<candidates.count {
20             let currentValue = candidates[i]
21             if currentValue > target || previousNum == currentValue {
22                 continue
23             }
24             var usdedNumsCopy = usdedNums
25             usdedNumsCopy.append(currentValue)
26             combinationSum(candidates, target-currentValue, i + 1, usdedNumsCopy)
27             previousNum = currentValue
28         }
29     }
30 }

20ms

 1 class Solution {
 2     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 3         var sortNums = candidates.sorted() 
 4         var tmp = [Int]()  // current set for testing
 5         var rlt = [[Int]]() // the result set
 6         backtrack(&sortNums, &tmp, 0, target, &rlt)
 7         return rlt
 8     }
 9 // subtrack a num from candidates to find the combination: 
10     func backtrack(_ nums: inout [Int], _ tmp: inout [Int], _ start:Int, _ tg:Int, _ rlt:inout[[Int]]) {
11         if tg==0 { // find one and put into result; 
12             rlt.append(tmp)
13             return
14         }
15         if start >= nums.count || nums[start] > tg { return } // go on condictions
16         for i in start...nums.count-1 {
17             if tg < nums[i] { return }
18             if i != start && nums[i]==nums[i-1] { continue } // skip the same num been used
19             tmp.append(nums[i])
20             backtrack(&nums, &tmp, i+1, tg-nums[i], &rlt) 
21             tmp.removeLast()
22         }
23     }
24 }

20ms

 1 class Solution {
 2     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 3   var results: [[Int]] = []
 4   
 5   // sort input first for removing dups
 6   let sortedCandidates = candidates.sorted()
 7   
 8   dfs(sortedCandidates, 0, [], target, &results)
 9   return results
10 }
11 
12 // 1. 递归的定义
13 private func dfs(_ nums: [Int], _ startIndex: Int, _ combinations: [Int], _ target: Int, _ results: inout [[Int]]) {
14   
15   // 3. 递归的出口
16   if target == 0 {
17     results.append(combinations)
18     return
19   }
20   
21   
22   for i in startIndex ..< nums.count {
23     
24     let number = nums[i]
25     
26     // skip dups
27     if i != startIndex, number == nums[i - 1] {
28       continue
29     }
30     
31     if target < number {
32       // since it's sorted array, we can just return from here
33       break
34     }
35     
36     // 2. 拆分
37     var mutableCombinations = combinations
38     mutableCombinations.append(number)
39     
40     // here we need to increment to i + 1, because each candidate can only used once in combination
41     dfs(nums, i + 1, mutableCombinations, target - number, &results)
42   }
43   
44 }
45     
46     func combinatio1nSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
47 
48         var result: [[Int]] = []
49         let sorted = candidates.sorted()
50         combinationSum2H(sorted, target, 0, [], &result)   
51         return result
52     }
53     
54        
55     func combinationSum2H(_ candidates: [Int], _ target: Int, _ start: Int, _ current: [Int], _ result: inout [[Int]]) {
56         if target == 0 {
57             result.append(current)
58             return
59         }
60         
61         if start >= candidates.count {
62             return
63         }
64         
65         
66         for i in start..<candidates.count {
67             let item = candidates[i]
68             if i > start && item == candidates[i-1] {
69                 continue
70             } 
71             combinationSum2H(candidates, target - item, i+1, current + [item], &result)   
72         }
73     }
74 }

24ms

 1 class Solution {
 2     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 3         var result = [[Int]]()
 4         var out = [Int]()
 5         var candidates = candidates.sorted()
 6         combinationSumDFS(candidates, target, 0, &out, &result)
 7         return result
 8     }
 9     
10     func combinationSumDFS(_ candidates: [Int], _ target: Int, _ start: Int, _ out: inout [Int], _ res: inout [[Int]]) {
11         if target == 0 {
12             res.append(out)
13         } else {
14             for i in start..<candidates.count {
15                 if i > start && candidates[i] == candidates[i - 1] {
16                     continue
17                 }
18                 guard target - candidates[i] >= 0 else {
19                     break
20                 }
21                 out.append(candidates[i])
22                 combinationSumDFS(candidates, target - candidates[i], i + 1, &out, &res)
23                 out.remove(at: out.count - 1)
24                 
25             }
26         }
27     }
28 }

 28ms

 1 class Solution {
 2     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 3         var result: [[Int]] = []
 4         var currentRes: [Int] = []
 5         recursionHelper(candidates.sorted(), target, 0, &currentRes, &result)
 6         return result
 7     }
 8 
 9     func recursionHelper(_ candidates: [Int], _ target: Int, _ index: Int,
10                          _ currentRes: inout [Int], _ result: inout [[Int]]) {
11         if target == 0 {
12             result.append(currentRes)
13             return
14         }
15         if index >= candidates.count {
16             return
17         }
18 
19         for idx in index..<candidates.count where target >= candidates[idx] {
20             if idx > index && candidates[idx - 1] == candidates[idx] {
21                 continue
22             }
23             currentRes.append(candidates[idx])
24             recursionHelper(candidates, target - candidates[idx], idx + 1, &currentRes, &result)
25             currentRes.removeLast()
26         }
27     }
28 }

32ms

 1 class Solution {
 2     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 3         var array = candidates.sorted()
 4         var result = [[Int]]()
 5         
 6         func helper(start: Int, temp: [Int], sum: Int) {
 7             if sum == target {
 8                 result.append(temp)
 9                 return
10             }
11             if start >= array.count || sum > target {
12                 return
13             }
14             for i in start ..< array.count {
15                 if sum + array[i] > target { return }
16                 if i != start && array[i] == array[i - 1] { continue }
17                 var temp = temp
18                 temp.append(array[i])
19                 helper(start: i + 1, temp: temp, sum: sum + array[i])
20             }
21         }
22         helper(start: 0, temp: [Int](), sum: 0)
23         return result    
24     }
25 }

 

36ms

 1 class Solution {
 2     func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 3         var result: [[Int]] = []
 4         var visited: [Bool] = Array(repeating: false, count: candidates.count)
 5         var currentRes: [Int] = []
 6         recursionHelper(candidates.sorted(), target, 0, &currentRes, &visited, &result)
 7         return result
 8     }
 9 
10     func recursionHelper(_ candidates: [Int], _ target: Int, _ index: Int,
11                          _ currentRes: inout [Int], _ visited: inout [Bool], _ result: inout [[Int]]) {
12         if target == 0 {
13             result.append(currentRes)
14             return
15         }
16         if index >= candidates.count {
17             return
18         }
19 
20         for idx in index..<candidates.count where !visited[idx] && target >= candidates[idx] {
21             if idx > 0 && candidates[idx - 1] == candidates[idx] && !visited[idx - 1] {
22                 continue
23             }
24             currentRes.append(candidates[idx])
25             visited[idx] = true
26             recursionHelper(candidates, target - candidates[idx], idx + 1, &currentRes, &visited, &result)
27             currentRes.removeLast()
28             visited[idx] = false
29         }
30     }
31 }

40ms

 1 class Solution {
 2     
 3   func combinationSum2(_ candidates: [Int], _ target: Int) -> [[Int]] {
 4         guard !candidates.isEmpty else { return [] }
 5         guard target > 0 else { return [[]] }
 6         
 7         var results = [[Int]]()
 8         var tempPath = [Int]()
 9         let sortedCandidates = candidates.sorted()
10         combinationSum(candidates: sortedCandidates, target: target, candidateIndex: -1, results: &results, path: &tempPath)
11         return results
12     }
13 
14     func combinationSum(candidates: [Int], target: Int, candidateIndex: Int, results: inout [[Int]], path: inout [Int]) {
15 
16         if target < 0 { return }
17         if target == 0 {
18             results.append(path)
19             return
20         }
21         
22         for i in (candidateIndex+1..<candidates.count) {
23             if candidates[i] > target { continue}
24             if i > candidateIndex+1, candidates[i] == candidates[i-1] {
25                 continue
26             }
27             path.append(candidates[i])
28             combinationSum(candidates: candidates, target: target - candidates[i],
29                            candidateIndex: i, results: &results, path: &path)
30             path.removeLast()
31             
32         }
33     }
34 }

 

posted @ 2018-11-03 17:06  为敢技术  阅读(534)  评论(0编辑  收藏  举报