簡體   English   中英

計划中lambda的重點是什么?

[英]What's the point of lambda in scheme?

我正在學習計划。 我知道如何使用lambda和let表達式。

然而,我正在努力弄清楚使用lambda的重點是什么。 你不能用lambda做你能做的一切嗎?

看一個lambda表達式是比let更好的選擇的例子會特別有用。

還有一件事 - 是否還有讓let比lambda更有用的情況? 如果是這樣的例子也會很好。

編輯:我也對對比定義和lambda感興趣,因為它們似乎執行類似的任務。


更新:

感謝大家的幫助。 在閱讀了你的答案之后,我做了一些更多的研究lambda / let / define,現在對它的了解要好得多。

我遇到了一個很酷的lambda用法的好例子 - 從程序中返回匿名函數。 例如,下面的過程operateTwice返回一個匿名函數,該函數基於傳入過程的參數:

(define operateTwice
  (lambda (op1 op2)
    (lambda (x y)
      (op2 (op1 x y) y))))

((operateTwice * +) 2 3) ;equivalent to: (+ (* 2 3) 3), or in standard notation 2*3+3

輸出:

9

一個let是一個lambda

例如

(let ((x 1))
  body)

可以翻譯成

((lambda (x) body) 1)

此外,在Scheme中, 所有控制和環境結構都可以由lambda表達式和lambdas的應用程序表示。

因此, lambdalet更強大,並且構成了Scheme中許多有趣結構的基礎。

關於definelambda ,頂級define會向頂級環境添加綁定。

當你寫作

(define (f x)
  body)

你真的在說

(define f (lambda (x) body))

嵌套定義被轉換為letrec ,也可以使用lambdas重寫。

所以,同樣,很多Scheme構造可以使用lambda轉換成某些東西,因此你很了解lambda是非常值得的。

如果要創建一個函數將其用作另一個函數的參數(例如map ),則使用lambda ,但實際上並不想命名該函數。

例如,如果要為列表中的每個數字添加42,則可以執行以下操作:

(define (add42 x) (+ x 42))
(map add42 (list 1 2 3 4))

但是如果你不想給你只使用一次的函數命名,你可以這樣做:

(map (lambda (x) (+ x 42)) (list 1 2 3 4))

實際上,它只是Lambda表達式的簡寫。 以下兩個表達式是等效的:

(let ((alpha 7)) (* 5 alpha))

((lambda (alpha) (* 5 alpha)) 7)

Lambda遵循語言的哲學,即一切都應該看起來像一個數學函數。 但在實踐中,如果變量太多,讓我們更容易弄清楚發生了什么。 想象一下10個變量,它們的值在Lambda塊之后定義,並且你試圖將每個變量與變量名稱相匹配,讓變量值放在它們的名稱旁邊,方便程序員使用,但更少符合功能編程理念。

Lambda可用於從更高階函數返回函數,但是不能這樣做。 例如:

(define (plus-list x)
  (cond ((number? x)
         (lambda (y) (+ (sum-n x) y)))
        ((list? x)
         (lambda (y) (+ (sum-list x) y)))
        (else (lambda (x) x))
        ))

> ((plus-list 3) 4)
10
> ((plus-list '(1 3 5)) 5)
14
> ((plus-list 'a) 5)
5

Lambda還可用於將函數傳遞給函數:

>(map (lambda (x) (+ 1 x)) '(-1 2 -3))
(0 3 -2)

lambda創建新的匿名函數,當然每次使用它們時都會對它們進行評估。

讓我們為值創建臨時名稱,並設置一次以便在let表單定義的范圍內使用。

他們真的是非常不同的野獸。

一些例子 :

(lambda(x)(* 5 x))

(let([x 2])(* 5 x))10(let([f(lambda(x)(* 5 x))])(f 2))10

first form創建一個乘以5的函數

第二種形式將2分配給x並將其乘以5得到10

第三,我們使用1的函數(多數為5)並將其作為參數調用2,結果也是10

在Scheme中,過程(或函數)是第一類對象,如列表,數字或字符串。 要創建列表文字,請使用名為list的原語:

> (define marks (list 33 40 56))
> marks
> (33 40 56)

就像這樣,要創建一個過程,可以使用lambda原語(或特殊形式):

> (define add-marks (lambda (m) (apply + m)))
> (add-marks marks)
> 129

由於過程是抽象的主要形式,Scheme為define提供了一個快捷方式define輕松綁定新過程:

> (define (add-marks m) (apply + m))

除此之外,過程就像所有其他第一類對象一樣。 它們可以作為參數傳遞給其他過程,並且過程可以評估以生成(或返回)另一個過程。

你可以這樣認為......你創建了一個使用另一個函數的函數,但是你想讓事情更加模塊化,所以你要做的就是把第二個函數作為第一個函數的參數調用,這樣你就有可能每當你覺得你需要另一種功能時改變第二種......希望這是有道理的

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM