0%

Problem 623


Problem 623


Lambda Count

The lambda-calculus is a universal model of computation at the core of functional programming languages. It is based on lambda-terms, a minimal programming language featuring only function definitions, function calls and variables. Lambda-terms are built according to the following rules:

  • Any variable x (single letter, from some infinite alphabet) is a lambda-term.
  • If M and N are lambda-terms, then (MN) is a lambda-term, called the application of M to N.
  • If x is a variable and M is a term, then (λx.M) is a lambda-term, called an abstraction. An abstraction defines an anonymous function, taking x as parameter and sending back M.

A lambda-term T is said to be closed if for all variables x, all occurrences of x within T are contained within some abstraction (λx.M) in T. The smallest such abstraction is said to bind the occurrence of the variable x. In other words, a lambda-term is closed if all its variables are bound to parameters of enclosing functions definitions. For example, the term (λx.x) is closed, while the term (λx.(xy)) is not because y is not bound.

Also, we can rename variables as long as no binding abstraction changes. This means that (λx.x) and (λy.y) should be considered equivalent since we merely renamed a parameter. Two terms equivalent modulo such renaming are called α-equivalent. Note that (λx.(λy.(xy))) and (λx.(λx.(xx))) are not α-equivalent, since the abstraction binding the first variable was the outer one and becomes the inner one. However, (λx.(λy.(xy))) and (λy.(λx.(yx))) are α-equivalent.

The following table regroups the lambda-terms that can be written with at most 15 symbols, symbols being parenthesis, λ, dot and variables.

(λx.x) (λx.(x(xx))) (λx.(λy.(yx))) (λx.((λy.x)x))
(λx.(x((xx)x))) (λx.(xx)) (λx.((xx)x)) (λx.(λy.(yy)))
(λx.((λy.y)x)) (λx.((xx)(xx))) (λx.(λy.x)) (λx.(λy.(xx)))
(λx.(x(λy.x))) ((λx.x)(λx.x)) (λx.((x(xx))x)) (λx.(λy.y))
(λx.(λy.(xy))) (λx.(x(λy.y))) (λx.(x(x(xx)))) (λx.(((xx)x)x))

Let Λ(n) be the number of distinct closed lambda-terms that can be written using at most n symbols, where terms that are α-equivalent to one another should be counted only once. You are given that Λ(6)=1, Λ(9)=2, Λ(15)=20 and Λ(35)=3166438.

Find Λ(2000). Give the answer modulo 1000000007.


lambda计数

lambda演算是作为函数式编程语言核心的一种通用计算模型。这种模型基于lambda项,这是一种只包含函数定义、函数调用和变量的极简编程语言。lambda项根据如下的规则进行构建:

  • 任意变量x(由单个字母表示,假定字母表的长度无穷)都是lambda项。
  • 如果MN是lambda项,那么(MN)也是lambda项,这被称为将M应用N上。
  • 如果x是一个变量而M是一个lambda项,那么(λx.M)是一个lambda项,这被称为抽象。 一个抽象定义了一个匿名函数,其中x是参数并返回M

如果在一个lambda项T中出现过的所有变量x均包含于T中的某个抽象(λx.M),则称T闭合的,并称包含x的抽象中最小的一个绑定x。换言之,如果一个lambda项中出现的所有变量都被绑定为某个函数定义中的参数,则它是闭合的。例如,lambda项(λx.x)是闭合的,而lambda项(λx.(xy))则不是,因为y并未被绑定。

另外,只要不改变抽象的绑定关系,我们可以随意重命名变量。这意味着(λx.x)(λy.y)应当被认为是等价的,因为我们只是重命名了一个参数。在这样的重命名中等价的两个lambda项被称为α-等价。注意(λx.(λy.(xy)))(λx.(λx.(xx)))并不是α-等价的,因为前者中绑定第一个变量的抽象是外层的抽象,而后者中则变成了内层的抽象。不过,(λx.(λy.(xy)))(λy.(λx.(yx)))α-等价的。

如下的表格展示了所有可以用至多15个符号表示的lambda项,这里的符号包括括号,λ,点号和变量名。

(λx.x) (λx.(x(xx))) (λx.(λy.(yx))) (λx.((λy.x)x))
(λx.(x((xx)x))) (λx.(xx)) (λx.((xx)x)) (λx.(λy.(yy)))
(λx.((λy.y)x)) (λx.((xx)(xx))) (λx.(λy.x)) (λx.(λy.(xx)))
(λx.(x(λy.x))) ((λx.x)(λx.x)) (λx.((x(xx))x)) (λx.(λy.y))
(λx.(λy.(xy))) (λx.(x(λy.y))) (λx.(x(x(xx)))) (λx.(((xx)x)x))

Λ(n)为可以用至多n个符号表示的不同闭合lambda项的数目,其中α-等价的lambda项只计算一次。已知Λ(6)=1Λ(9)=2Λ(15)=20以及Λ(35)=3166438

Λ(2000),并将答案对1000000007取模。


Gitalking ...