2016-04-12 27 views
2

Standart sıralama yaklaşımını değiştirmeyi ve daha az arabirimi sıralamak için belirli bir rastgelelik eklemeyi denedim. zamanGolang Sıralama paketi - Bulanık sıralama hatası

if (u[i] - u[j]) <= 0 

veya

Ama

if (u[i] - u[j]) <= rv 

durum bazı infazlar sonra panik üretir beklendiği gibi çalıştığını

if u[i] < u[j] 

package main 
import ( 
    "crypto/rand" 
    "fmt" 
    "math/big" 
    "sort" 
) 

type FuzzySorter []float64 

func (u FuzzySorter) Len() int { 
    return len(u) 
} 
func (u FuzzySorter) Swap(i, j int) { 
    u[i], u[j] = u[j], u[i] 
} 
func (u FuzzySorter) Less(i, j int) bool { 
    pom, _ := rand.Int(rand.Reader, big.NewInt(int64(2))) 
    rv := float64(pom.Int64()) 
    if (u[i] - u[j]) <= rv { 
     return true 
    } else { 
     return false 
    } 

} 
func (u FuzzySorter) Sort() FuzzySorter { 
    sort.Sort(u) 
    return u 
} 

func main() { 
    unsorted := FuzzySorter{ 
     0, 
     1, 
     1, 
     1, 
     1, 
     6, 
     0, 
     4, 
     6, 
     1, 
     1, 
     1, 
     0, 
     2, 
     8, 
     1, 
     5, 
     4, 
     6, 
     6, 
     6, 
     16, 
     12, 
     6, 
     1, 
     1, 
     1, 
     0, 
     0, 
     11, 
     2, 
     14, 
     16, 
     6, 
     12, 
     0, 
     4, 
     1, 
     0, 
     16, 
     2, 
     6, 
     0, 
     0, 
     0, 
     0, 
     1, 
     11, 
     1, 
     0, 
     2, 
     1, 
     1, 
     1, 
     1, 
     0, 
     1, 
     12, 
     10, 
     1, 
     5, 
     2, 
     6, 
     4, 
     1, 
     0, 
     0, 
     11, 
     1, 
     1, 
     2, 
     2, 
     1, 
     0, 
     0, 
     1, 
     0, 
     1, 
     17, 
     2, 
     1, 
     1, 
     2, 
     0, 
     3, 
     7, 
     1, 
     5, 
     1, 
     0, 
     1, 
     0, 
     0, 
     0, 
     1, 
     3, 
     1, 
     1, 
     1, 
     2, 
     1, 
     0, 
     3, 
     1, 
     6, 
     1, 
     1, 
     0, 
     1, 
     12, 
     0, 
     1, 
     1, 
     0, 
     1, 
     0, 
     0, 
     6, 
     1, 
     2, 
     2, 
     0, 
     0, 
     2, 
     1, 
     1, 
     0, 
     4, 
     4, 
     1, 
     1, 
     1, 
     0, 
     1, 
     1, 
     1, 
     2, 
     0, 
     0, 
     1, 
     0, 
     1, 
     2, 
     1, 
     2, 
     1, 
     1, 
     0, 
     0, 
     4, 
     1, 
     0, 
     1, 
     0, 
     1, 
     1, 
     3, 
     1, 
     0, 
    } 
    unsorted.Sort() 
    fmt.Println(unsorted) 

} 

https://play.golang.org/p/4AxNRN4VD7

panik mesajı

Bildiğim kadarıyla o örn iki negatif karşılaştırmalar bekliyoruz Git sıralama uygulanmasını anlayabileceği şekilde
panic: runtime error: index out of range 

goroutine 1 [running]: 
panic(0x176ba0, 0x1040a010) 
    /usr/local/go/src/runtime/panic.go:464 +0x700 
main.FuzzySorter.Less(0x10456000, 0x9f, 0x9f, 0x19, 0xffffffff, 0x4, 0x1, 0xd) 
    /tmp/sandbox201242525/main.go:21 +0x140 
main.(*FuzzySorter).Less(0x10434140, 0x19, 0xffffffff, 0x5c, 0x1, 0x10434140) 
    <autogenerated>:3 +0xc0 
sort.doPivot(0xfef741b0, 0x10434140, 0x19, 0x9f, 0x7, 0x19) 
    /usr/local/go/src/sort/sort.go:128 +0x280 
sort.quickSort(0xfef741b0, 0x10434140, 0x19, 0x9f, 0xe, 0xfef741b0) 
    /usr/local/go/src/sort/sort.go:195 +0xa0 
sort.Sort(0xfef741b0, 0x10434140) 
    /usr/local/go/src/sort/sort.go:229 +0x80 
main.FuzzySorter.Sort(0x10456000, 0x9f, 0x9f, 0x1, 0x0, 0x0, 0x0, 0x1777a0) 
    /tmp/sandbox201242525/main.go:29 +0xa0 
main.main() 
    /tmp/sandbox201242525/main.go:195 +0xc0 
+4

Az yöntem deterministik olmalıdır, yani yazma, küçükten büyüğe sıralanır. – JimB

+3

Daha az işlevi değiştirmek yerine çıkışı çekin. –

+0

Felsefi olarak tamamen katılıyorum. Teknik olarak, bunun bir şekilde uygulanacağı anlamına mı geliyor? Yani - sen bir belirsizliğe sahip olmanın “Less()” in bir paniğe neden olacağını/söyleyeceğini mi söylüyorsun? –

cevap

0

. Less(i, j) ve Less(j, i), her ikisi de eşitlik olarak kabul edilen ancak pozitif olmayan yanlış döndürür. E.g Less(i, j) ve Less(j, i) her ikisi de doğru olamaz. Yani kolayca, sadece

if (u[i] - u[j]) < -1 { 
     return true 
    } else { 
     return false 
    } 

https://play.golang.org/p/VcKI9uzcM9

0

Go 1.8 itibariyle yeni türlerini tanımlamak için sizi gerektirmeyen bir dilim sıralamak için daha kolay bir yolu yoktur, mantık açısından doğru ve deterministik yolu istenen sonucu elde edebilirsiniz. Sadece daha az (anonim) bir lambda yaratırsınız.

a := []int{5, 3, 4, 7, 8, 9} 
sort.Slice(a, func(i, j int) bool { 
    return a[i] < a[j] 
}) 
for _, v := range a { 
    fmt.Println(v) 
} 

Bu tam tersini istiyorsanız, basitçe hep aynı sonucu üretmek zorundadır aynı 2 değerleri için daha az çağıran a[i] < a[j]