2014-10-31 58 views
0

對於ML中的作業分配,我必須使用摺疊函數和匿名函數將整數列表變成交替和。如果列表爲空,則結果爲0.這是迄今爲止我所擁有的。我認爲我所擁有的是正確的,但是我最大的問題是我無法弄清楚如何編寫我作爲一個匿名函數。任何幫助將不勝感激。ML匿名函數交替總和

fun foldl f y nil = y 
    | foldl f y (x::xr) = 
    foldl f(f(x,y))xr; 

    val sum = foldl (op -) ~6[1,2,3,4,5,6]; 

    val sum = foldl (op -) ~4[1,2,3,4]; 

    val sum = foldl (op -) ~2[1,2]; 

這些都只是一些例子,我測試,看看有什麼我工作過,我覺得這三個是正確的。

回答

1

有兩種情況:一種是列表長度是偶數,一種是列表長度是奇數。如果我們有一個清單[a,b,c,d,e]那麼交替的總和是a - b + c - d + e。你可以重新寫爲

e - (d - (c - (b - a)))

如果列表有偶數長度,例如[a,b,c,d]那麼我們就可以寫出它的交替和作爲

- (d - (c - (b - a)))

因此,爲了解決這兩種情況,我們可以讓我們的fold的累加器是一個三元組,如果列表是奇數,那麼第一個條目是正確的值,如果列表是偶數,第二個條目是正確的值,第三個值告訴我們我們看過的元素的數量,最後我們可以用它來知道答案是第一個還是第二個條目。

所以像

fn (x,y,n) => (x - #1 y, ~(x + #2 y), n + 1) 

匿名函數會工作,我們可以與foldl用的(0,0,0)起動蓄電池使用它,所以

fun alternating_sum xs = 
    let 
    (v1, v2, n) = foldl (fn (x,y,n) => (x - #1 y, ~(x + #2 y), n + 1)) (0,0,0) xs 
    in 
    if n mod 2 = 0 then v2 else v1 
    end