How do I reverse an array in Go?
http://play.golang.org/p/W70J4GU7nA
1 2 3 4 | s := []int{5, 2, 6, 3, 1, 4} sort.Reverse(sort.IntSlice(s)) fmt.Println(s) // 5, 2, 6, 3, 1, 4 |
很难理解func Reverse(data Interface)Interface中的含义。
如何反转数组? 我不需要排序。
老实说,这个简单到足以让我像这样写出来:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | package main import"fmt" func main() { s := []int{5, 2, 6, 3, 1, 4} for i, j := 0, len(s)-1; i < j; i, j = i+1, j-1 { s[i], s[j] = s[j], s[i] } fmt.Println(s) } |
http://play.golang.org/p/vkJg_D1yUb
(其他答案很好地解释了
通常,要对整数数组进行排序,可以将它们包装在
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | type reverse struct { // This embedded Interface permits Reverse to use the methods of // another Interface implementation. Interface } // Less returns the opposite of the embedded implementation's Less method. func (r reverse) Less(i, j int) bool { return r.Interface.Less(j, i) } // Reverse returns the reverse order for data. func Reverse(data Interface) Interface { return &reverse{data} } |
因此,当您编写
我迟到了2年,但出于娱乐和兴趣,我想提出一个"赔率"解决方案。
假设任务确实是要反转列表,那么对于原始性能,bgp的解决方案可能是无与伦比的。它通过前后交换数组项来简单有效地完成工作,此操作在数组和切片的随机访问结构中非常有效。
在函数式编程语言中,惯用方法通常涉及递归。在Go中看起来有些奇怪,并且性能会很差。也就是说,这是一个递归数组反转函数(在一个小的测试程序中):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | package main import ( "fmt" ) func main() { myInts := []int{ 8, 6, 7, 5, 3, 0, 9 } fmt.Printf("Ints %v reversed: %v ", myInts, reverseInts(myInts)) } func reverseInts(input []int) []int { if len(input) == 0 { return input } return append(reverseInts(input[1:]), input[0]) } |
输出:
1 | Ints [8 6 7 5 3 0 9] reversed: [9 0 3 5 7 6 8] |
同样,这只是出于娱乐目的,而不是为了生产。如果列表太大,不仅速度很慢,而且还会使堆栈溢出。我刚刚进行了测试,它将反转100万个x31的列表,但是崩溃了1000万个。
首先,如果要反转数组,请执行以下操作,
1 2 3 | for i, j := 0, len(a)-1; i < j; i, j = i+1, j-1 { a[i], a[j] = a[j], a[i] } |
然后,在golang.org中查看Reverse的用法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | package main import ( "fmt" "sort" ) func main() { s := []int{5, 2, 6, 3, 1, 4} // unsorted sort.Sort(sort.Reverse(sort.IntSlice(s))) fmt.Println(s) } // output // [6 5 4 3 2 1] |
并查看反向和排序的描述
1 2 | func Reverse(data Interface) Interface func Sort(data Interface) |
Sort sorts data. It makes one call to data.Len to determine n, and O(n*log(n)) calls to data.Less and data.Swap. The sort is not guaranteed to be stable.
因此,如您所知,Sort不仅是一种排序算法,还可以将其视为工厂,当您使用Reverse时,它只是返回一个反向排序算法,Sort只是在进行排序。
这是更通用的切片反向功能。如果输入不是切片,它将惊慌。
1 2 3 4 5 6 7 8 | //panic if s is not a slice func ReverseSlice(s interface{}) { size := reflect.ValueOf(s).Len() swap := reflect.Swapper(s) for i, j := 0, size-1; i < j; i, j = i+1, j-1 { swap(i, j) } } |
如果要反转阵列,则可以按相反的顺序进行。由于该语言中没有"反向范围"原语(至少现在还没有),因此您必须执行以下操作(http://play.golang.org/p/AhvAfMjs_7):
1 2 3 4 5 6 7 8 | s := []int{5, 2, 6, 3, 1, 4} for i := len(s) - 1; i >= 0; i-- { fmt.Print(s[i]) if i > 0 { fmt.Print(",") } } fmt.Println() |
关于是否很难理解
它只是使排序所需的比较"相反"。
1 | func Reverse(data Interface) Interface |
这意味着它需要一个
顺便说一句,如果您单击文档中的函数名称,它将直接链接到
这是一个简单的Go解决方案,它使用高效的方法(无需额外的内存)来反转数组:
1 2 3 4 5 6 7 | i := 0 j := len(nums) - 1 for i < j { nums[i], nums[j] = nums[j], nums[i] i++ j-- } |
想法是反转数组等效于在中心交换每个元素及其镜像。
https://play.golang.org/p/kLFpom4LH0g
这是另一种方法
1 2 3 4 5 6 7 | func main() { example := []int{1, 25, 3, 5, 4} sort.SliceStable(example, func(i, j int) bool { return true }) fmt.Println(example) } |
https://play.golang.org/p/-tIzPX2Ds9z
从Golang Wiki SliceTricks:
To replace the contents of a slice with the same elements but in
reverse order:
1
2
3
4 for i := len(a)/2-1; i >= 0; i-- {
opp := len(a)-1-i
a[i], a[opp] = a[opp], a[i]
}The same thing, except with two indices:
1
2
3 for left, right := 0, len(a)-1; left < right; left, right = left+1, right-1 {
a[left], a[right] = a[right], a[left]
}
要在适当的位置反转数组,请迭代到其中点,然后将每个元素替换为其" mirror element":
1 2 3 4 5 6 7 8 9 10 | func main() { xs := []int{1, 2, 3, 4, 5, 6, 7, 8, 9} itemCount := len(xs) for i := 0; i < itemCount/2; i++ { mirrorIdx := itemCount - i -1 xs[i], xs[mirrorIdx] = xs[mirrorIdx], xs[i] } fmt.Printf("xs: %v ", xs) } |
https://play.golang.org/p/JeSApt80_k
这是我反转数组的解决方案:
1 2 3 4 5 6 7 8 9 10 11 | func reverse_array(array []string) []string { lenx := len(array) // lenx holds the original array length reversed_array := make([]string, lenx) // creates a slice that refer to a new array of length lenx for i := 0; i < lenx; i++ { j := lenx - (i + 1) // j initially holds (lenx - 1) and decreases to 0 while i initially holds 0 and increase to (lenx - 1) reversed_array[i] = array[j] } return reversed_array } |
您可以在户外游乐场尝试该解决方案
1 2 3 4 5 6 7 8 9 | package main import"fmt" func main() { array := []string{"a","b","c","d"} fmt.Println(reverse_array(array)) // prints [d c b a] } |
不要反转它,保持它现在不变,然后向后迭代。