2014-02-23 47 views
3

我有以下代碼片段開始,並且我不知道我的錯誤在哪裏。目標是傳入兩個值valfac,並輸出表格[val1, val1*fac,val1*fac*fac...]的列表,但不起作用。如何使用haskell中的元素與元素之間的可變距離

gm :: Int -> Int -> [Int] 
gm val fac = let j=0 in 
[ if (x==val) then x else if (x==(val+1)) then k else j 
| x <- [val..], let k = val*fac, let j = fac*k] 

例如,如果我叫gm 2 3我應該得到的結果[2,6,18,54,162...]但我得到的是[2,6,18,18,18...]

回答

5

我覺得你正試圖直接將命令式算法轉換成Haskell。定義這種無限列表的標準方法是使用懶惰和遞歸:如果你想使用列表理解

gm val fac = val : gm (val * fac) fac 

gm val fac = [val * fac^i | i <- [1..]] 
+0

這幫助。我忘了「^」運算符。這就是我所需要的,謝謝。 – cHam

2

要回答爲什麼你的代碼不能正常工作,請記住,有沒有在列表內涵可變的變量。該表顯示得到的是如何生成的列表作爲x前進通過值valval+1,...

x k  j     x == val? x == val+1? element 
--------------------------------------------------------- ------- 
val val*fac fac*k = val*val*fac True  False  val   (x) 
val+1 val*fac fac*k = val*val*fac False  True  val*fac  (k) 
val+2 val*fac fac*k = "   False  False  val*val*fac (j) 
val+3 val*fac fac*k = "   False  False  val*val*fac (j) 
... 

所以你可以看到,kj不會改變,因爲它們在常量來定義valfac

這是一個建議你的列表Haskell的方式。首先構建這個序列:

[ 1, fac, fac*fac, fac*fac*fac, ...] 

然後將map (val*)應用到它。

要生成的權力序列中,有幾個辦法:

1)這是(*fac)功能迭代的列表。也就是說,定義:

f x = fac*x 

然後權力清單:

[ 1, f 1, f (f 1), f (f (f 1)), ... ] 

,這意味着你可以使用iterate功能從前奏。 2)請注意,冪序列的尾部是該序列的map (*fac)。因此,可以編寫:

powers x = 1 : map (*x) (powers x) 

這是基本相同的:(1),但有時更容易發現的序列,且其尾之間的關係。

3

我認爲你可以這樣做:

gm' val fac = iterate (*fac) val 

輸出:

*Main> take 5 $ gm' 2 3 
[2,6,18,54,162] 

與方法的問題是,你列出的理解只能包含三個值,val, k, j