冒泡排序
package main
import "fmt"
//定義一個排序的接口
type SortInterface interface {
sort();
}
//定義額排序的結構體
type Sortor struct {
name string
}
func main() {
arry :=[]int{12,15,6,8,4,3,18,3,7}
learnsort := Sortor{name: "冒泡排序"}
learnsort.sort(arry)
fmt.Println(learnsort.name, arry)
}
//結構體實現接口,嵌套循環實現冒泡排序
func(sorter Sortor) sort(arry []int){
done := true
arrylength :=len(arry)
for i:=0; i<arrylength && done; i++{
done = false
for j := 0; j < arrylength-i-1; j++ {
done = true
if arry[j] > arry[j+1] {
t :=arry[j]
arry[j] = arry[j+1]
arry[j+1] = t
}
}
}
}
快速排序
快速排序原理不多廢話,直接上代碼
package main
import "fmt"
func main(){
arry :=[]int{12,15,6,8,4,3,18,3,7}
sort2(arry, 0, len(arry)-1)
fmt.Println(arry)
}
//快速排序代碼
func sort2(arry []int, low int, high int) {
startIndex :=low
endIndex :=high
key :=arry[0]
for endIndex > startIndex {
for endIndex > startIndex && arry[endIndex] >= key {
endIndex--
}
if arry[endIndex] <= key {
temp := arry[endIndex]
arry[endIndex] = arry[startIndex]
arry[startIndex] = temp
}
for endIndex > startIndex && arry[startIndex] <= key {
startIndex++
}
if arry[startIndex] >= key {
temp := arry[startIndex]
arry[startIndex] = arry[endIndex]
arry[endIndex] = temp
}
}
if startIndex > low{
sort2(arry, low, startIndex-1)
}
if endIndex < high{
sort2(arry, endIndex+1, high)
}
}
//結果是[3 3 6 4 7 8 12 18 15]
簡單選擇排序
package main
import "fmt"
func main() {
arry :=[]int{12,15,6,8,4,3,18,3,7}
sort3(arry)
fmt.Println(arry)
}
//從前往後排,篩選出最小的往前移動
func sort3(arry1 []int) {
for i := 0; i < len(arry1)-1; i++{
k := j;
for j := k+1; j < len(arry1); j++{
if arry1[j] < arry1[k]{
k = j
}
}
if i != k {
temp := arry1[i]
arry1[i] = arry1[k]
arry1[k] = temp
}
}
}
堆排序
package main
import (
"fmt"
)
//堆排序
//s[0]不用,實際元素從角標1開始
//父節點元素大於子節點元素
//左子節點角標爲2*k
//右子節點角標爲2*k+1
//父節點角標爲k/2
func HeapSort(s []int) {
N := len(s) - 1 //s[0]不用,實際元素數量和最後一個元素的角標都爲N
//構造堆
//如果給兩個已構造好的堆添加一個共同父節點,
//將新添加的節點作一次下沉將構造一個新堆,
//由於葉子節點都可看作一個構造好的堆,所以
//可以從最後一個非葉子節點開始下沉,直至
//根節點,最後一個非葉子節點是最後一個葉子
//節點的父節點,角標爲N/2
for k := N / 2; k >= 1; k-- {
sink(s, k, N)
}
//下沉排序
for N > 1 {
swap(s, 1, N) //將大的放在數組後面,升序排序
N--
sink(s, 1, N)
}
}
//下沉(由上至下的堆有序化)
func sink(s []int, k, N int) {
for {
i := 2 * k
if i > N { //保證該節點是非葉子節點
break
}
if i < N && s[i+1] > s[i] { //選擇較大的子節點
i++
}
if s[k] >= s[i] { //沒下沉到底就構造好堆了
break
}
swap(s, k, i)
k = i
}
}
func swap(s []int, i int, j int) {
s[i], s[j] = s[j], s[i]
}
func main() {
s := []int{-1,9, 0, 6, 5, 8, 2, 1, 7, 4, 3}
fmt.Println(s[1:])
HeapSort(s)
fmt.Println(s[1:])
}
直接插入排序
package main
import(
"container/list"
"fmt"
)
func main(){
s := []int{9,0,6,5,8,2,1,7,4,3}
fmt.Println(s)
InsertionSort(s)
fmt.Println(s)
}
func InsertionSort(s []int) {
n := len(s)
if n < 2 {
return
}
for j := 1; j < n; j++ {
for j := i; j > 0 && s[j] < s[j - 1]; j-- {
swap(s, j, j - 1)
}
}
}
//交換
func swap(slice []int, j int, j int) {
slice[j], slice[j] = slice[j], slice[j]
}
希爾排序
希爾排序的實質就是分組插入排序,該方法又稱縮小增量排序,因DL.Shell於1959年提出而得名。
該方法的基本思想是:先將整個待排元素序列分割成若干個子序列(由相隔某個“增量”的元素組成的)分別進行直接插入排序,然後依次縮減增量再進行排序,待整個序列中的元素基本有序(增量足夠小)時,再對全體元素進行一次直接插入排序。因爲直接插入排序在元素基本有序的情況下(接近最好情況),效率是很高的,因此希爾排序在時間效率上比前兩種方法有較大提高。
package main
import(
"fmt"
)
func main(){
s := []int{9,0,6,5,8,2,1,7,4,3}
fmt.Println(s)
ShellSort(s,len(s))
fmt.Println(s)
}
func ShellSort(arry []int, n int) {
for gap :=n/2; gap>0; gap/=2{
for i :=gap; i<n; i++ {
for j :=i-gap; j>=0 && arry[j] > arry[j+gap]; j -= gap {
arry[j] , arry[j+gap] = arry[j+gap] , arry[j]
}
}
}
}
合併排序
合併排序算法是用分治策略實現對N個元素進行排序的算法。其基本思想是:
將待排序元素分成大小大致相同 的兩個子集合,分別 對兩個子集合進行排序,最終將排好序的子集合合併成所要求的排好序的集合。
一句話概括就是將一段數據分成前後兩個的數組進行大小比較(分治到每一個小塊都是2個),然後再合併進行比較
package main
import "fmt"
func main() {
arr01:=[]int{4,3,20,7,10,9,11,2}
fmt.Print("排序前")
fmt.Println(arr01)
mergeSort(arr01,0,len(arr01)-1)
fmt.Print("排序後")
fmt.Println(arr01)
}
func mergeSort(arr []int,low,high int){
if low<high{
mid:=(low+high)/2
fmt.Println(arr)
fmt.Println(low)
fmt.Println(mid)
fmt.Println(high)
mergeSort(arr,low,mid)
mergeSort(arr,mid+1,high)
merge1(arr,low,mid,high)
}
}
func merge1(arr []int,low,mid,high int){
leftLen:=mid-low+1
rightLen:=high-mid
arrLeft:=make([]int,leftLen+1)
for i:=0;i<leftLen;i++{
arrLeft[i]=arr[low+i]
}
arrLeft[leftLen]=99999//哨兵牌
arrRight:=make([]int,rightLen+1)
for j:=0;j<rightLen;j++{
arrRight[j]=arr[mid+j+1]
}
arrRight[rightLen]=99999//哨兵牌
fmt.Println(arrRight)
fmt.Println(arrLeft)
i,j:=0,0
for k:=low;k<=high;k++{
if arrLeft[i]<=arrRight[j]{
arr[k]=arrLeft[i]
i++
}else{
arr[k]=arrRight[j]
j++
}
}
}