-
Notifications
You must be signed in to change notification settings - Fork 116
/
Copy pathpermutations.go
87 lines (83 loc) · 1.63 KB
/
permutations.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
package permutations
import (
//"fmt"
)
// recursion
func permute(nums []int) [][]int {
return traverse(nums, map[int]bool{}, []int{})
}
func traverse(nums []int, m map[int]bool, solution []int) (rets [][]int) {
if len(nums) == 0 {
return [][]int{}
}
if len(nums) == 1 {
return [][]int{[]int{nums[0]}}
}
if len(solution) == len(nums) {
replia := make([]int, len(solution))
copy(replia, solution)
rets = append(rets, replia)
return
}
for i, num := range nums {
if m[i] {
continue
}
m[i] = true
solution = append(solution, num)
rets = append(rets, traverse(nums, m, solution)...)
delete(m, i)
solution = solution[:len(solution)-1]
}
return rets
}
// no recursion
func permute1(nums []int) [][]int {
if len(nums) == 0 {
return [][]int{}
}
if len(nums) == 1 {
return [][]int{[]int{nums[0]}}
}
visited := map[int]bool{}
// depth==-1 means the root
depth, maxDepth := -1, len(nums)-1
currentIndex := make([]int, maxDepth+1)
for i := 0; i < maxDepth; i++ {
currentIndex[i] = -1
}
stack := []int{}
ret := [][]int{}
for {
L:
for depth < maxDepth {
for {
childDepth := depth + 1
if currentIndex[childDepth] == len(nums)-1 {
currentIndex[childDepth] = -1
break L
}
currentIndex[childDepth]++
val := nums[currentIndex[childDepth]]
if !visited[val] {
stack = append(stack, val)
visited[val] = true
break
}
}
depth++
}
if depth == maxDepth {
tmp := make([]int, len(stack))
copy(tmp, stack)
ret = append(ret, tmp)
}
depth--
if depth == -2 {
break
}
visited[stack[len(stack)-1]] = false
stack = stack[:len(stack)-1]
}
return ret
}