2016-03-29 12 views
-3

Bir kayan nokta değeri listesi almak istediğimi söyle, sonra bir noktada "toplam" ve "uzunluk" (işlevlerde yerleşik) kullanmam gerekiyor. Kayan nokta değerlerinin rasgele uzunluk listesinin ortalamasını hesaplayan bir işlev yapabilir misiniz?Ön tanımlı işlevleri kullanmadan bir listenin ortalamasını nasıl alırım?

+1

"Evet"? Sonuçta, sadece kendi 'length' ve' sum' yazabilirsiniz. Bununla birlikte, "toplamı" ve "uzunluk" kombinasyonunun genellikle sorunlara yol açtığını unutmayın. – Zeta

+0

Neden sorun yaşıyorum? –

+0

çünkü "length" genellikle bir "Int" döndürür ve bir "Float" (toplam) 'ın Carsten

cevap

1

foldl' öğesini kullanarak hem çalışanların sayımını hem de çalışan toplamı içeren bir tuple oluşturabilir ve ardından ortalamayı almak için bölebilirsiniz.

data StrictPair a b = StrictPair !a !b 

myAvg :: Fractional a => [a] -> a 
myAvg [] = error "Empty list" 
myAvg list = 
    let 
    tupleSum (StrictPair count sum) x = StrictPair (count + 1) (sum + x) 
    StrictPair totalCount totalSum = foldl' tupleSum (StrictPair 0 0) list 
    in 
    totalSum/totalCount 

hafıza sorunları önlemek için foldl' ve StrictPair kuvvet değerlendirilmesi kullanımı. (Öneri için teşekkürler, @Jubobs, @Zeta ve @dfeuer!)

+2

Çok fazla thunks: p Ara değerlerin zorla değerlendirilmesiyle birlikte sol katlama, benim düşüncemde daha anlamlı olacaktır. Richard Bird, kitabının 7. bölümünde, Haskell * ile işlevsel olarak düşünmenin tam olarak nasıl yapıldığını gösterir. – Jubobs

+0

@Jubobs, Bird'ün "veri çifti" ye eşdeğer yaklaşımıdır. – Zeta

+0

@Zeta Esasen, evet. – Jubobs

1

Hayır, genel olarak bu imkansızdır. Bir sayı listesinin ortalamasını hesaplamak için toplama ve bölme gereklidir. Bunları Rational gibi standart türler için hesaplama işlevleri "yerleşik" dir.

İlgili konular