2010-07-03 17 views
1

我有一個問題,爲什麼我在F#中得到某些結果。我有以下代碼...F# - 需要幫助的人解釋懶惰函數,爲什麼我得到了一定的結果

let lHelloWorld = lazy(printfn "Lazy Hello World"; 30+30) 
let aHelloWorld = (printfn "Active Hello World"; 30+30) 

printfn "lazy value is %d" lHelloWorld.Value 
printfn "lazy value is %d" lHelloWorld.Value 
printfn "active value is %d" aHelloWorld 
printfn "active value is %d" aHelloWorld 

我的輸出如下...

Active Hello World 
Lazy Hello World 
lazy value is 60 
lazy value is 60 
active value is 60 
active value is 60 

什麼我不明白這是爲什麼?是主動打招呼世界printfn被前所示懶惰的你好詞?我希望在「Active Hello World」之前展示「Lazy Hello World」?

如果有人能幫助解釋這一點,將不勝感激。

回答

1

嗯,我不是一個很大的F#人,但它設置了惰性模式,所以他們在請求之前不會做任何事情。所以當你用懶惰包裝它時,直到你真正使用它纔會運行。但是,由於您沒有將其用於活動用戶,因此只要它被分配就會執行該功能。

這只是一個猜測,雖然我不是F#的傢伙。

這裏有一篇文章解釋它。 http://weblogs.asp.net/podwysocki/archive/2008/03/21/adventures-in-f-f-101-part-6-lazy-evaluation.aspx

很抱歉忘了附上鍊接。

+0

我本來以爲我會打電話給懶惰的功能力,它被稱爲? – 2010-07-03 05:10:00

+0

那麼您正在請求該值,以便觸發變量中的延遲函數以運行並分配結果。由於第一個賦值被惰性包裝,所以基本上被忽略並且未被賦值。但第二個人打電話給打印,然後進行分配。當你第一次請求它時,懶惰的會被分配。 – spinon 2010-07-03 05:19:11

+0

好吧..從我身邊的金髮時刻 - 出於某種原因,我認爲這些功能只有在需要時纔會被調用,並帶有副作用。 現在我們來看看IC#的術語,它似乎是爲了聲明它們而默認創建的「函數」 - 但是隻有在第一次使用它時纔會創建一個懶惰函數,而不管它的順序如何聲明。 – 2010-07-03 05:25:57

6

這裏是我的註釋說明

// Here we go... 
let lHelloWorld = lazy(printfn "Lazy Hello World"; 30+30) 
// Ok, we defined a value called lHelloWorld. The right hand side is 
// a lazy(...), so we don't evaluate the ..., we just store it in a 
// System.Lazy object and assign that value to lHelloWorld. 

let aHelloWorld = (printfn "Active Hello World"; 30+30) 
// Ok, we're defining a value called aHelloWorld. The right hand side is 
// a normal expression, so we evaluate it it right now. Which means we 
// print "Active Hello World", and then compute 30+30=60, and assign the 
// final result (60) to aHelloWorld. 

// Note that neither of the previous two entities are functions. 


// Now we have some effects: 
printfn "lazy value is %d" lHelloWorld.Value 
// Calling .Value on an object of type System.Lazy will either 
// - force the value if it has not yet been evaluated, or 
// - return the cached value if it was previously evaluated 
// Here we have not yet evaluated it, so we force the evaluation, 
// which prints "Lazy Hello World" and then computes 30+30=60, and then 
// stores the final 60 value in the lHelloWorld's cache. Having evaluated 
// the arguments to the printfn on this line of code, we can now call that 
// printfn, which prints "lazy value is 60". 

printfn "lazy value is %d" lHelloWorld.Value 
// This time, calling .Value just fetches the already-computed cached value, 
// 60, and so this just prints "lazy value is 60". 

printfn "active value is %d" aHelloWorld 
// aHelloWorld has type 'int'. Its value is 60. This is trivial, 
// it prints "active value is 60". 
printfn "active value is %d" aHelloWorld 
// Ditto. 
+0

Brian ...謝謝!這真的幫助我瞭解訂單... – 2010-07-03 08:42:46

相關問題