En informática, una expresión "let" asocia la definición de una función con un ámbito restringido .
La expresión "let" también puede definirse en matemáticas, donde asocia una condición booleana con un ámbito restringido.
La expresión "let" puede considerarse como una abstracción lambda aplicada a un valor. En matemáticas, una expresión "let" también puede considerarse como una conjunción de expresiones dentro de un cuantificador existencial que restringe el alcance de la variable.
La expresión `let` está presente en muchos lenguajes funcionales para permitir la definición local de una expresión, que luego se utiliza para definir otra. En algunos lenguajes funcionales, la expresión `let` se presenta en dos formas: `let` o `let rec`. `let rec` es una extensión de la expresión `let` simple que utiliza el combinador de punto fijo para implementar la recursión .
Historia
El lenguaje LCF de Dana Scott [ 1 ] fue una etapa en la evolución del cálculo lambda hacia los lenguajes funcionales modernos. Este lenguaje introdujo la expresión `let`, que ha aparecido en la mayoría de los lenguajes funcionales desde entonces.
Los lenguajes Scheme , [ 2 ] ML y, más recientemente, Haskell [ 3 ] han heredado expresiones let de LCF.
Los lenguajes imperativos con estado, como ALGOL y Pascal, implementan esencialmente una expresión `let` para definir un alcance restringido de las funciones en las estructuras de bloques.
Una cláusula " where " estrechamente relacionada, junto con su variante recursiva " where rec ", apareció ya en The mechanical evaluation of expressions de Peter Landin . [ 4 ]
Descripción
Una expresión "let" define una función o valor para su uso en otra expresión. Además de ser una construcción utilizada en muchos lenguajes de programación funcional , es una construcción del lenguaje natural que se usa frecuentemente en textos matemáticos. Es una construcción sintáctica alternativa a una cláusula "where".
En ambos casos, la estructura completa es una expresión cuyo valor es 5. Al igual que en la estructura if-then-else, el tipo devuelto por la expresión no es necesariamente booleano.
Una expresión let viene en 4 formas principales,
En los lenguajes funcionales, la expresión `let` define funciones que pueden ser llamadas dentro de la expresión. El alcance del nombre de la función se limita a la estructura de la expresión `let`.
En matemáticas, la expresión `let` define una condición, que constituye una restricción sobre la expresión. La sintaxis también puede admitir la declaración de variables cuantificadas existencialmente, locales a la expresión `let`.
La terminología, la sintaxis y la semántica varían de un lenguaje a otro. En Scheme , `let` se usa para la forma simple y `let rec` para la forma recursiva. En ML, `let` marca solo el inicio de un bloque de declaraciones, mientras que `fun` marca el inicio de la definición de la función. En Haskell, `let` puede ser mutuamente recursivo , y el compilador determina qué se necesita.
Definición
Una abstracción lambda representa una función sin nombre. Esta es una fuente de inconsistencia en la definición de una abstracción lambda. Sin embargo, las abstracciones lambda pueden componerse para representar una función con nombre. De esta forma se elimina la inconsistencia. El término lambda,
es equivalente a definir la funciónporen la expresión, que puede escribirse como la expresión let ;
La expresión `let` se entiende como una expresión en lenguaje natural. Representa la sustitución de una variable por un valor. La regla de sustitución describe las implicaciones de la igualdad como sustitución.
Definición de "Dejemos de lado" en matemáticas.
En matemáticas, la expresión `let` se describe como la conjunción de expresiones. En lenguajes funcionales, también se utiliza para limitar el alcance. En matemáticas, el alcance se describe mediante cuantificadores. La expresión `let` es una conjunción dentro de un cuantificador existencial.
donde E y F son de tipo booleano.
La expresión let permite que la sustitución se aplique a otra expresión. Esta sustitución puede aplicarse dentro de un ámbito restringido, a una subexpresión. El uso natural de la expresión let es en la aplicación a un ámbito restringido (llamado lambda droping ). Estas reglas definen cómo se puede restringir el ámbito;
donde F no es de tipo booleano . A partir de esta definición se puede derivar la siguiente definición estándar de una expresión let, tal como se usa en un lenguaje funcional.
Para simplificar, el marcador que especifica la variable existencial,, se omitirá de la expresión cuando quede claro por el contexto.
Derivación
Para obtener este resultado, primero supongamos que:
entonces
Utilizando la regla de sustitución,
así que para todo L ,
Dejardonde K es una nueva variable. Entonces,
Entonces,
Pero desde la interpretación matemática de una reducción beta,
Aquí, si y es una función de una variable x, no es la misma x que en z. Se puede aplicar el cambio de nombre alfa. Por lo tanto, debemos tener,
entonces,
Este resultado se representa en un lenguaje funcional de forma abreviada, donde el significado es inequívoco;
Aquí, la variable x se reconoce implícitamente como parte de la ecuación que define x, y como la variable en el cuantificador existencial.
No se permite levantar desde Boolean
Surge una contradicción si E se define por. En este caso,
se convierte,
y utilizando,
Esto es falso si G es falso. Para evitar esta contradicción, no se permite que F sea de tipo booleano. Para F booleano, la declaración correcta de la regla de eliminación utiliza implicación en lugar de igualdad,
Puede parecer extraño que se aplique una regla diferente para Boolean que para otros tipos. La razón de esto es que la regla,
Esto solo aplica cuando F es booleano. La combinación de ambas reglas crea una contradicción, por lo que cuando una regla se cumple, la otra no.
Uniendo expresiones let
Las expresiones pueden definirse con múltiples variables,
entonces se puede derivar,
entonces,
Leyes que relacionan el cálculo lambda y las expresiones let
La reducción Eta proporciona una regla para describir las abstracciones lambda. Esta regla, junto con las dos leyes derivadas anteriormente, define la relación entre el cálculo lambda y las expresiones let.
Sea la definición definida a partir del cálculo lambda.
Para evitar los posibles problemas asociados con la definición matemática , Dana Scott definió originalmente la expresión `let` a partir del cálculo lambda. Esto puede considerarse como la definición constructiva o ascendente de la expresión `let` , en contraste con la definición matemática axiomática o descendente.
La expresión let simple y no recursiva se definió como azúcar sintáctico para la abstracción lambda aplicada a un término. En esa definición,
La definición de la expresión simple let se extendió posteriormente para permitir la recursión utilizando el combinador de punto fijo .
Combinador de punto fijo
El combinador de punto fijo puede representarse mediante la expresión,
Esta representación puede convertirse en un término lambda. Una abstracción lambda no admite referencia al nombre de la variable en la expresión aplicada, por lo que x debe pasarse como parámetro a x .
Utilizando la regla de reducción de eta,
da,
Una expresión let puede expresarse como una abstracción lambda usando,
da,
Esta es posiblemente la implementación más sencilla de un combinador de punto fijo en cálculo lambda. Sin embargo, una reducción beta proporciona la forma más simétrica del combinador Y de Curry.
expresión let recursiva
La expresión recursiva llamada "let rec" se define utilizando el combinador Y para expresiones recursivas de let.
Expresión let mutuamente recursiva
Este enfoque se generaliza para admitir la recursión mutua. Una expresión `let` recursiva mutua se puede componer reorganizando la expresión para eliminar cualquier condición `and`. Esto se logra reemplazando múltiples definiciones de función con una sola definición de función, que iguala una lista de variables a una lista de expresiones. Luego se utiliza una versión del combinador Y, llamado combinador de punto fijo polivariádico Y* [ 5 ], para calcular el punto fijo de todas las funciones simultáneamente. El resultado es una implementación recursiva mutua de la expresión `let` .
Valores múltiples
Una expresión `let` puede usarse para representar un valor que es miembro de un conjunto,
Bajo la aplicación de funciones , de una expresión let a otra,
Pero se aplica una regla diferente al aplicar la expresión let a sí misma.
No parece existir una regla sencilla para combinar valores. Se requiere una expresión general que represente una variable cuyo valor pertenezca a un conjunto de valores. Esta expresión debe basarse en la variable y el conjunto.
La aplicación de una función a esta forma debería generar otra expresión con la misma forma. De este modo, cualquier expresión sobre funciones con múltiples valores puede tratarse como si tuviera un solo valor.
No basta con que la forma represente únicamente el conjunto de valores. Cada valor debe tener una condición que determine cuándo la expresión toma dicho valor. La construcción resultante es un conjunto de pares de condiciones y valores, denominado «conjunto de valores». Véase la reducción de conjuntos de valores algebraicos .
Reglas para la conversión entre el cálculo lambda y las expresiones let.
Se proporcionarán metafunciones que describen la conversión entre expresiones lambda y let . Una metafunción es una función que recibe un programa como parámetro. El programa actúa como datos para el metaprograma. El programa y el metaprograma se encuentran en diferentes metaniveles.
Se utilizarán las siguientes convenciones para distinguir el programa del metaprograma,
- Los corchetes [] se utilizarán para representar la aplicación de funciones en el metaprograma.
- En el metaprograma, las variables se representarán con letras mayúsculas. En el programa, las variables se representarán con letras minúsculas.
- se utilizará para igualdades en el metaprograma.
Para simplificar, se aplicará la primera regla que indique coincidencias. Las reglas también presuponen que las expresiones lambda se han preprocesado de manera que cada abstracción lambda tenga un nombre único.
También se utiliza el operador de sustitución. La expresiónSignifica sustituir cada aparición de G en L por S y devolver la expresión. La definición utilizada se extiende para abarcar la sustitución de expresiones, a partir de la definición proporcionada en la página del cálculo lambda . La comparación de expresiones debe verificar la equivalencia alfa (cambio de nombre de las variables).
Conversión de expresiones lambda a expresiones let
Las siguientes reglas describen cómo convertir una expresión lambda en una expresión let , sin alterar la estructura.
La regla 6 crea una variable única V, que sirve como nombre para la función.
Ejemplo
Por ejemplo, el combinador Y ,
se convierte en,
Conversión de expresiones `let` a expresiones lambda
Estas reglas revierten la conversión descrita anteriormente. Convierten una expresión `let` en una expresión `lambda`, sin alterar la estructura. No todas las expresiones `let` pueden convertirse utilizando estas reglas. Las reglas asumen que las expresiones ya están organizadas como si hubieran sido generadas por `de-lambda` .
En el cálculo lambda, no existe un equivalente estructural exacto para las expresiones `let` que contienen variables libres utilizadas recursivamente. En este caso, se requiere la adición de parámetros. Las reglas 8 y 10 añaden estos parámetros.
Las reglas 8 y 10 son suficientes para dos ecuaciones recursivas entre sí en la expresión `let` . Sin embargo, no funcionan para tres o más ecuaciones recursivas entre sí. El caso general requiere un nivel adicional de bucle, lo que complica un poco la metafunción. Las siguientes reglas reemplazan a las reglas 8 y 10 en la implementación del caso general. Se han mantenido las reglas 8 y 10 para que se pueda estudiar primero el caso más simple.
- lambda-form - Convierte la expresión en una conjunción de expresiones, cada una de la forma variable = expresión .
- ...... donde V es una variable.
- lift-vars : Obtiene el conjunto de variables que necesitan X como parámetro, porque la expresión tiene X como variable libre.
- subvariables : Para cada variable del conjunto, sustitúyala por la variable aplicada a X en la expresión. Esto convierte a X en una variable pasada como parámetro, en lugar de ser una variable libre en el lado derecho de la ecuación.
- de-let - Elevar cada condición en E de modo que X no sea una variable libre en el lado derecho de la ecuación.
Ejemplos
Por ejemplo, la expresión let obtenida del combinador Y ,
se convierte en,
Para un segundo ejemplo, tomemos la versión elevada del combinador Y ,
se convierte en,
Para un tercer ejemplo, la traducción de,
es,
Por cuarto ejemplo, la traducción de,
es,
que es el famoso combinador y .
Personas clave
Véase también
Referencias
- ↑ "PCF es un lenguaje de programación para funciones computables, basado en LCF, la lógica de funciones computables de Scott" ( Plotkin 1977 ) . Programación de funciones computables es utilizado por ( Mitchell 1996 ) . También se le conoce como Programación con funciones computables o Lenguaje de programación para funciones computables .
- ↑ "Esquema - Variables y expresiones Let" .
- ↑ Simon, Marlow (2010). "Informe del lenguaje Haskell 2010 - Expresiones Let" .
- ↑ Landin, Peter J. (1964). "La evaluación mecánica de expresiones" . The Computer Journal . 6 (4). British Computer Society : 308–320 . doi : 10.1093/comjnl/ 6.4.308 .
- ↑ "Combinadores de punto fijo polivariádicos más simples para recursión mutua" .
Obras citadas
- Cálculo lambda