""" A simple version of symbolic regression. Defaultly we use Galileo's ball rolling data (see below) """ # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Define the grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ TERMINAL_WEIGHT = 5.0 from LOTlib3.Grammar import Grammar grammar = Grammar() grammar.add_rule('START', '', ['EXPR'], 1.0) grammar.add_rule('EXPR', '(%s + %s)', ['EXPR', 'EXPR'], 1.0) # or use plus_ grammar.add_rule('EXPR', '(%s * %s)', ['EXPR', 'EXPR'], 1.0) # or use times_ grammar.add_rule('EXPR', 'divide_', ['EXPR', 'EXPR'], 1.0) # use a version safe to division by zero grammar.add_rule('EXPR', '(%s - %s)', ['EXPR', 'EXPR'], 1.0) # or use subtract_ grammar.add_rule('EXPR', 'exp_', ['EXPR'], 1.0) grammar.add_rule('EXPR', 'log_', ['EXPR'], 1.0) grammar.add_rule('EXPR', 'pow_', ['EXPR', 'EXPR'], 1.0) # including this gives lots of overflow grammar.add_rule('EXPR', 'sin_', ['EXPR'], 1.0) grammar.add_rule('EXPR', 'cos_', ['EXPR'], 1.0) grammar.add_rule('EXPR', 'tan_', ['EXPR'], 1.0)
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ from LOTlib3.Grammar import Grammar grammar = Grammar() grammar.add_rule('START', '', ['QUANT'], 1.0) # Very simple -- one allowed and required quantifier grammar.add_rule('QUANT', 'exists_', ['FUNCTION', 'SET'], 1.00) grammar.add_rule('QUANT', 'forall_', ['FUNCTION', 'SET'], 1.00) # The thing we are a function of grammar.add_rule('SET', 'S', None, 1.0) # And allow us to create a new kind of function grammar.add_rule('FUNCTION', 'lambda', ['BOOL'], 1.0, bv_type='OBJECT') # Logical connectives grammar.add_rule('BOOL', 'and_', ['BOOL', 'BOOL'], 1.0) grammar.add_rule('BOOL', 'or_', ['BOOL', 'BOOL'], 1.0) grammar.add_rule('BOOL', 'not_', ['BOOL'], 1.0) # non-terminal arguments get passed as normal python arguments grammar.add_rule( 'BOOL', 'is_color_', ['OBJECT', '\'red\''], 5.00) # --> is_color_(OBJECT, 'red') --> OBJECT.color == 'red' grammar.add_rule('BOOL', 'is_color_', ['OBJECT', '\'blue\''], 5.00) grammar.add_rule('BOOL', 'is_color_', ['OBJECT', '\'green\''], 5.00)
fn = FunctionNode(None, 'EXPR', 'apply_', [copy(args[0]), copy(args[1])]) for i in range(2, len(args)): fn = FunctionNode(fn, 'EXPR', 'apply_', [fn, copy(args[i])]) try: return lambda_reduce(fn) except RuntimeError: return None if __name__ == "__main__": ## Make a simple grammar for lambda calculus from LOTlib3.Grammar import Grammar G = Grammar() # Here, rules creating smaller lambdas are higher prob; created simpler lambdas are also higher prob G.add_rule('START', '', ['EXPR'], 1.0) G.add_rule('EXPR', 'lambda', ['EXPR'], 2.0, bv_type='EXPR', bv_args=None, bv_p=2.0) G.add_rule('EXPR', 'apply_', ['EXPR', 'EXPR'], 1.0) # And print some expressions and reduce for _ in range(1000): t = G.generate()
# -*- coding: utf-8 -*- # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Now that's a simple grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ from LOTlib3.Grammar import Grammar grammar = Grammar() grammar.add_rule('START', '', ['EXPR'], 1.0) grammar.add_rule('EXPR', 'lambda', ['EXPR'], 2.0, bv_type='EXPR', bv_args=None, bv_p=5.0) grammar.add_rule('EXPR', 'apply_', ['EXPR', 'EXPR'], 1.0) # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Define a simple grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ from math import log from LOTlib3.Hypotheses.Lexicon.SimpleLexicon import SimpleLexicon from LOTlib3.Hypotheses.LOTHypothesis import LOTHypothesis from LambdaEvaluation import lambda_reduce, lambdastring, compose_and_reduce, EvaluationException from LOTlib3.Miscellaneous import qq, Infinity, attrmem
""" This folder defines a bunch of "standard" grammars. In each, we do NOT specify the terminals, which typically expand the nonterminal PREDICATE->... """ from LOTlib3.Grammar import Grammar DEFAULT_FEATURE_WEIGHT = 5.0 # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ SimpleBoolean_noTF = Grammar() SimpleBoolean_noTF.add_rule('START', '', ['BOOL'], 1.0) SimpleBoolean_noTF.add_rule('BOOL', 'and_', ['BOOL', 'BOOL'], 1.0) SimpleBoolean_noTF.add_rule('BOOL', 'or_', ['BOOL', 'BOOL'], 1.0) SimpleBoolean_noTF.add_rule('BOOL', 'not_', ['BOOL'], 1.0) SimpleBoolean_noTF.add_rule('BOOL', '', ['PREDICATE'], DEFAULT_FEATURE_WEIGHT) # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ SimpleBoolean = Grammar() SimpleBoolean.add_rule('START', 'False', None, 1.0) SimpleBoolean.add_rule('START', 'True', None, 1.0) SimpleBoolean.add_rule('START', '', ['BOOL'], 1.0) SimpleBoolean.add_rule('BOOL', 'and_', ['BOOL', 'BOOL'], 1.0) SimpleBoolean.add_rule('BOOL', 'or_', ['BOOL', 'BOOL'], 1.0)
""" A simple exmaple to show use of a Lexicon """ WORDS = ['even', 'odd'] # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ from LOTlib3.Grammar import Grammar from LOTlib3.Miscellaneous import q grammar = Grammar() grammar.add_rule('START', '', ['BOOL'], 1.) grammar.add_rule('BOOL', '(%s == %s)', ['NUMBER', 'NUMBER'], 1.) grammar.add_rule('BOOL', '(not %s)', ['BOOL'], 1.) grammar.add_rule('BOOL', '(%s and %s)', ['BOOL', 'BOOL'], 1.) grammar.add_rule('BOOL', '(%s or %s)', ['BOOL', 'BOOL'], 1.) # use the short_circuit form grammar.add_rule('NUMBER', 'x', None, 1.) grammar.add_rule('NUMBER', '1', None, 1.) grammar.add_rule('NUMBER', '0', None, 1.) grammar.add_rule('NUMBER', 'plus_', ['NUMBER', 'NUMBER'], 1.) grammar.add_rule('NUMBER', 'minus_', ['NUMBER', 'NUMBER'], 1.) for w in WORDS: grammar.add_rule('BOOL', 'lexicon', [q(w), 'NUMBER'], 1.) # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Data
def make_data(size=1, alpha=0.99): return [FunctionData(input=['aaaa'], output=True, alpha=alpha), FunctionData(input=['aaab'], output=False, alpha=alpha), FunctionData(input=['aabb'], output=False, alpha=alpha), FunctionData(input=['aaba'], output=False, alpha=alpha), FunctionData(input=['aca'], output=True, alpha=alpha), FunctionData(input=['aaca'], output=True, alpha=alpha), FunctionData(input=['a'], output=True, alpha=alpha)] * size # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ from LOTlib3.Grammar import Grammar grammar = Grammar() grammar.add_rule('START', '', ['EXPR'], 1.0) grammar.add_rule('EXPR', '(%s*)', ['EXPR'], 1.0) grammar.add_rule('EXPR', '(%s?)', ['EXPR'], 1.0) grammar.add_rule('EXPR', '(%s+)', ['EXPR'], 1.0) grammar.add_rule('EXPR', '(%s|%s)', ['EXPR', 'EXPR'], 1.0) grammar.add_rule('EXPR', '%s%s', ['TERMINAL', 'EXPR'], 5.0) grammar.add_rule('EXPR', '%s', ['TERMINAL'], 5.0) for v in 'abc.': grammar.add_rule('TERMINAL', v, None, 1.0) # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Hypothesis
# all possible data sets on 10 objects all_possible_data = [('', set(sample_sets_of_objects(n, all_objects))) for n in range(1, 10)] # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ # Grammar # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ from LOTlib3.Grammar import Grammar from LOTlib3.Miscellaneous import q # The priors here are somewhat hierarchical by type in generation, tuned to be a little more efficient # (but the actual RR prior does not care about these probabilities) grammar = Grammar() grammar.add_rule('START', '', ['WORD'], 1.0) grammar.add_rule('BOOL', 'and_', ['BOOL', 'BOOL'], 1. / 3.) grammar.add_rule('BOOL', 'or_', ['BOOL', 'BOOL'], 1. / 3.) grammar.add_rule('BOOL', 'not_', ['BOOL'], 1. / 3.) grammar.add_rule('BOOL', 'True', None, 1.0 / 2.) grammar.add_rule('BOOL', 'False', None, 1.0 / 2.) # note that this can take basically any types for return values grammar.add_rule('WORD', '(%s if %s else %s)', ['WORD', 'BOOL', 'WORD'], 0.5) grammar.add_rule('WORD', q('undef'), None, 0.5) # grammar.add_rule('WORD', 'if_', ['BOOL', 'WORD', q('undef')], 0.5)