builtup4/bu4/parsing/lcall.py
2021-07-24 02:34:37 +03:00

61 lines
1.9 KiB
Python

from bu4.codes import CODE_CALL
from bu4.evaluation.avcall import AVCall
from bu4.evaluation.elinked import ELinked
from bu4.linking.afterlinking import AfterLinking
from bu4.linking.allambda import ALLambda
from bu4.parsing.linked import Linked, Parsed, LinkingState
from bu4.linking.linkingfinished import LinkingFinished
from bu4.linking.linkingparsed import LinkingParsed
from bu4.evaluation.aftervalue import envtype, Evaluable, AfterValue
__all__ = ('LCall', 'PCall',)
class LCall(Linked):
argument: Linked
lambda_: Linked
def __init__(self, promise: set[bytes], argument: Parsed, lambda_: Parsed):
self.promise = promise
self._argument = argument
self._lambda = lambda_
def link(self) -> LinkingState:
return AfterLinking(
LinkingParsed(self.promise, self._argument),
ALLambda(self._given_argument)
)
def _given_argument(self, argument: Linked) -> LinkingState:
self.argument = argument
return AfterLinking(
LinkingParsed(self.promise, self._lambda),
ALLambda(self._given_lambda)
)
def _given_lambda(self, lambda_) -> LinkingState:
self.lambda_ = lambda_
self.future = self.argument.future | self.lambda_.future
return LinkingFinished(self)
def evaluable(self, env: envtype) -> Evaluable:
return AfterValue(ELinked(env, self.lambda_), AVCall(env, self.argument))
def __str__(self):
return f'/{self.argument}{self.lambda_}'
def unlink(self) -> Parsed:
return PCall(self._argument, self._lambda)
class PCall(Parsed):
def __init__(self, value: Parsed, lambda_: Parsed):
self.value = value
self.lambda_ = lambda_
def link(self, promise: set[bytes]) -> Linked:
return LCall(promise, self.value, self.lambda_)
def __bytes__(self):
return bytes([CODE_CALL, *bytes(self.value), *bytes(self.lambda_)])