#FIXME this is an awkward dependence, I don't know where else to put to_term_bindings though import strings import booleans from frozendict import frozendict import functions import lists import termtypes from termtypes import is_type from ipdb import set_trace as debug cons = T.dict_cons empty = T.empty_dict dict_type = termtypes.new_type("the type of dictionaries") termtypes.set_types(dict_type, cons, empty) image = term.simple("the function that maps a dictionary to the image of [k] in that dictionary", "k") @getter(image.head, cons.head) def cons_image(asker, k, key, value, other): if booleans.ask_firmly(asker, builtins.equal(k, key)): return asker.reply(answer=value) else: return asker.ask_tail( fields.get_field(image(k), other), handler=asker.pass_through(not_found.head) ) @getter(image.head, empty.head)
import term from term import Term as T import fields import termtypes pair_type = termtypes.new_type("the type of pairs") termtypes.set_type(pair_type, T.pair) def to_pair(asker, p): return (fields.get(asker, first(), p), fields.get(asker, second(), p)) first = fields.named_binding( "the function that maps a pair to its first element", T.pair.head, 'a' ) second = fields.named_binding( "the function that maps a pair to its second element", T.pair.head, 'b' )
import properties import fields from frozendict import frozendict import askers import termtypes #Representing terms-------------------------------- #TODO I could probably make Representation a function, #then make a decorator that turns any such function into a "held" #version... quoted_term = term.simple("a term with head [head] head and bindings [bindings]", 'head', 'bindings') term_type = termtypes.new_type("the type of terms") termtypes.set_type(term_type, quoted_term) head = fields.named_binding( "the function that maps a term to its head", quoted_term.head, 'head' ) bindings = fields.named_binding( "the function that maps a term to its bindings", quoted_term.head, 'bindings' ) #referent_of = term.simple("the function that maps a term to the referent of [s] in that term's head", "s")
import functions import convert from convert import converter, is_reducible import builtins from builtins import builtin import fields from fields import getter, setter import properties from properties import checker import updates from updates import updater import termtypes from termtypes import is_type list_type = termtypes.new_type("the type of lists") @is_type(list_type) @as_head(T.empty_list.head) def empty(): return T.empty_list() @is_type(list_type) @converter(T.cons.head) def cons(asker, req, head, tail): return asker.ask_tail(make_list(req, empty(), T.cons(head, tail), empty())) @is_type(list_type) @as_head("the list with last element [last] and first elements [init]") def snoc(init, last): return T(snoc.head, init=init, last=last)
import term from term import Term as T from dispatch import Dispatcher import updates from updates import updater import convert from convert import converter import termtypes from termtypes import is_type int_type = termtypes.new_type("the type of integers") #Canonicalization--------------------------------- #TODO convert other things def to_int(asker, k): if k.to_int() is not None: return k.to_int() return literalizer.dispatch(asker, k) literalizer = Dispatcher("int literalizer", ('integer',)) @is_type(int_type) @literalizer(T.negative.head) def literalize_negative(asker, x): return -to_int(asker, x) @is_type(int_type) @literalizer(T.double.head) def literalize_double(asker, x): return 2*to_int(asker, x)
import fields from dispatch import Dispatcher import convert import term from term import Term as T import ints import builtins import termtypes from termtypes import is_type string_type = termtypes.new_type("the type of strings") char_type = termtypes.new_type("the type of characters") #Converting to strings---------------------------- #TODO the default representations of characters, lists, strings, etc. #have a distinguished place, because they can be quickly manipulated #there needs to be some way for that to come through (eventually) #FIXME I'd like to memoize this, but it's hard because of the dependence on the asker #in reality I'm basically happy to ignore that, as with convert #I could write another cache here... #maybe best is to make a new asker-ignoring id-based cache def to_str(asker, s): if s.to_str() is not None: return s.to_str() result = literalizer.dispatch(asker, s) if result is not None: return result else: chars = fields.get(asker, list_of_chars(), s)