2016-02-16 26 views
7

Bạn tôi cho tôi thấy điều này và tôi thực sự tò mò tại sao nó hoạt động như thế này. lúc đầu tôi nghĩ rằng đó là sẽ là một lỗi cú pháp, nhưng nó không ... Here're một số thí nghiệm của tôi:(lambda lambda lambda) là gì?

> (lambda lambda lambda) 
#<procedure> 
> ((lambda lambda lambda)) 
'() 
> ((lambda lambda lambda) 1 2 3 4 5 6 7) 
'(1 2 3 4 5 6 7) 
> (lambda lambda foo) 
#<procedure> 
> ((lambda lambda foo)) 
foo: undefined; 
cannot reference an identifier before its definition 
> (lambda lambda 1 2 3 4 5) 
#<procedure> 
> ((lambda lambda 1 2 3 4 5)) 
5 
> (lambda foo lambda) 
. lambda: bad syntax in: lambda 
> (lambda 1 2 3) 
. lambda: bad argument sequence in: 1 
> ((lambda) 1 2 3) 
. lambda: bad syntax in: (lambda) 

Vì vậy, có vẻ như:

  1. Trong lambda, lambda thể là arg-ids?
  2. Trong lambda, lambda có thể là một hàm tạo danh sách?

Trả lời

7

Ohhh Tôi hiểu rồi. lambda có thể bị che khuất!

> ((lambda (lambda) (+ 1 lambda)) 7) 
8 

Ngoài ra, cú pháp được đưa ra tại https://docs.racket-lang.org/guide/lambda.html là không hoàn toàn đúng vì ở arg-ids vị trí, một định danh có thể có mặt ở đó! Điều này sẽ liên kết danh sách các đối số với số nhận dạng:

> ((lambda foo foo) 1 2 3 4) 
'(1 2 3 4) 

Các giải thích này!

+1

Liên kết này có thêm chi tiết: https://docs.racket-lang.org/reference/lambda.html –

+0

Thx :) Trên thực tế, liên kết tôi đã đăng đề cập đến 'rest-id' cũng như trong 4.4.1, nhưng tôi không thấy nó! –

+1

Có. Tuy nhiên, có một trường hợp kỳ lạ hơn mà điều này không giải thích được. '(lambda lambda foo)' = '# '. Và đó là bởi vì đây là trong một REPL, nơi bạn có thể làm '(define (f x) foo)' và sau đó xác định foo sau đó, để ví dụ đệ quy lẫn nhau hoạt động. Nhưng đối với những điều này, bạn thực sự nên đặt chúng trong một tập tin, bởi vì đó là những gì sẽ cho thấy hành vi thực sự của họ. Trong một tập tin của chính nó, '(lambda lambda foo)' sẽ là một lỗi, như nó cần. –