Definendo un combinatore, che:
è definito come un termine lambda senza variabili libere, quindi, per definizione, qualsiasi combinatore è già un termine lambda,
è possibile definire, per esempio, una struttura della lista, scrivendo:
Y = (list definition in lambda calculus)
Y LIST = (list definition in lambda calculus) LIST
Y LIST = (element insertion definition in lambda calculus)
Intuitivamente, e utilizzando un combinatore punto fisso, una possibile definizione è - considerare \ = lambda:
- un elenco è vuoto, seguito da un elemento finale, ad esempio
0
;
- o una lista è formata da un elemento
x
, che potrebbe essere un'altra lista all'interno della precedente.
Poiché è stato definito con un combinatore - combinatore di punti fissi -, non è necessario eseguire ulteriori applicazioni, la seguente astrazione è un termine lambda stesso.
Y = \f.\y.\x.f (x y)
Ora, chiamandolo una lista:
Y LIST = (*\f*.\y.\x.*f* (x y)) *LIST* -- applying function name
LIST = \y.\x.LIST (x y), and adding the trailing element "0"
LIST = (\y.\x.LIST (x y)) 0
LIST = (*\y*.\x.LIST (x *y*)) *0*
LIST = \x.LIST (x 0), which defines the element insertion abstraction.
Il punto fisso combinatore Y
, o semplicemente Combinator, permette di prendere in considerazione la definizione di LIST già un utente valida, senza variabili libere, in modo da , senza necessità di riduzioni.
Quindi, è possibile aggiungere/inserire elementi, diciamo 1 e 2, facendo:
LIST = (\x.LIST (x 0)) 1 2 =
= (*\x*.LIST (*x* 0)) *1* 2 =
= (LIST (1 0)) 2 =
Ma qui, sappiamo la definizione di lista, così abbiamo espanderlo:
= (LIST (1 0)) 2 =
= ((\y.\x.LIST (x y)) (1 0)) 2 =
= ((*\y*.\x.LIST (x *y*)) *(1 0)*) 2 =
= (\x.LIST (x (1 0))) 2 =
ora, inserendo elemenet 2
:
= (\x.LIST (x (1 0))) 2 =
= (*\x*.LIST (*x* (1 0))) *2* =
= LIST (2 (1 0))
che possono sia essere ampliato, in caso di un nuovo inserimento, o r semplicemente lasciato come è, a causa del fatto che LIST è un termine lambda, definito con un combinatore.
espansione per inserimenti futuri:
= LIST (2 (1 0)) =
= (\y.\x.LIST (x y)) (2 (1 0)) =
= (*\y*.\x.LIST (x *y*)) *(2 (1 0))* =
= \x.LIST (x (2 (1 0))) =
= (\x.LIST (x (2 (1 0)))) (new elements...)
Sono davvero contento sono stato in grado di ricavare questo me stesso, ma sono abbastanza sicuro che ci deve essere qualche buon gruppo di condizioni di troppo, quando si definisce una stack, un heap o una struttura più elaborata.
Cercando di ricavare l'astrazione di inserimento pila/rimozione - senza tutto il passo-passo:
Y = \f.\y.\x.f (x y)
Y STACK 0 = \x.STACK (x 0)
STACK = \x.STACK (x 0)
Per eseguire l'operazione su di essa, chiamiamolo uno stack vuoto - allocare una variabile (:
stack = \x.STACK (x 0)
// Insertion -- PUSH STACK VALUE -> STACK
PUSH = \s.\v.(s v)
stack = PUSH stack 1 =
= (\s.\v.(s v)) stack 1 =
= (\v.(stack v)) 1 =
= (stack 1) = we already know the steps from here, which will give us:
= \x.STACK (x (1 0))
stack = PUSH stack 2 =
= (\s.\v.(s v)) stack 2 =
= (stack 2) =
= \x.STACK x (2 (1 0))
stack = PUSH stack 3 =
= (\s.\v.(s v)) stack 3 =
= (stack 3) =
= \x.STACK x (3 (2 (1 0)))
E noi, ancora una volta, il nome di questo risultato, per noi per far apparire i elementi:
stack = \x.STACK x (3 (2 (1 0)))
// Removal -- POP STACK -> STACK
POP = \s.(\y.s (y (\t.\b.b)))
stack = POP stack =
= (\s.(\y.s y (\t.\b.b))) stack =
= \y.(stack (y (\t.\b.b))) = but we know the exact expansion of "stack", so:
= \y.((\x.STACK x (3 (2 (1 0)))) (y (\t.\b.b))) =
= \y.STACK y (\t.\b.b) (3 (2 (1 0))) = no problem if we rename y to x (:
= \x.STACK x (\t.\b.b) (3 (2 (1 0))) =
= \x.STACK x (\t.\b.b) (3 (2 (1 0))) = someone guide me here, if i'm wrong
= \x.STACK x (\b.b) (2 (1 0)) =
= \x.STACK x (2) (1 0) =
= \x.STACK x (2 (1 0))
Per cosa, si spera, abbiamo spuntato l'elemento 3
.
Ho provato a ricavarlo da solo, quindi, se c'è qualche restrizione dal calcolo lambda, non l'ho seguito, per favore, segnalalo.
Non è uno stack perfettamente collegato con 'push' =' cons' e 'pop' =' testa/coda'? Ne parlo perché le liste collegate singolarmente sono già state fatte migliaia di volte e potrebbero essere più facili da pensare. – delnan
@delnan Questo è vicino all'approccio che ho proposto nella mia risposta, in quanto ho usato parte della definizione 'list' per definire lo' stack'. – Rubens