def getSubFormulaNoParent(formula, objects): elements = set() edges = set() if formula.key == 'not': formula = next(iter(formula.children)) if formula.key == 'intends': raise NameError('no intends yet') else: lit = Literal(name=formula.key, num_args=len(formula.children), truth=False) elements.add(lit) elif formula.key == 'intends': raise NameError('no intends yet') elif formula.type > 0: raise ValueError('not sure why formula.type > 0') else: lit = Literal(name=formula.key, num_args=len(formula.children), truth=True) elements.add(lit) for i, child in enumerate(formula.children): # children are list arg = next(ob_element for ob_name, ob_element in objects.items() if child.key == ob_name) edges.add(Edge(lit, arg, i)) elements.add(arg) return elements, edges
def makeGoal(formula): if formula.key == 'not': formula = next(iter(formula.children)) num_children = len(formula.children) lit = Literal(name=formula.key, num_args=num_children, truth=False) else: num_children = len(formula.children) lit = Literal(name=formula.key, num_args=num_children, truth=True) return lit
def createElementByType(parameter, decomp, p_type_dict): if 'character' in parameter.types: elm = Actor(typ='character', arg_name=parameter.name) elm.p_types = p_type_dict[parameter] elif 'actor' in parameter.types: elm = Actor(typ='actor', arg_name=parameter.name) elm.p_types = p_type_dict[parameter] elif 'person' in parameter.types: elm = Actor(typ='person', arg_name=parameter.name) elm.p_types = p_type_dict[parameter] elif 'arg' in p_type_dict[parameter] or 'item' in p_type_dict[ parameter] or 'place' in p_type_dict[parameter]: arg_type = next(iter(parameter.types)) elm = Argument(typ=arg_type, arg_name=parameter.name) elm.p_types = p_type_dict[parameter] elif 'step' in parameter.types or 'step-s' in parameter.types or 'step-d' in parameter.types or 'step-c' in parameter.types: elm = Operator(arg_name=parameter.name) elif 'literal' in parameter.types or 'lit' in parameter.types: elm = Literal(arg_name=parameter.name) else: # assume its type object, treat as Argument. arg_type = next(iter(parameter.types)) elm = Argument(typ=arg_type, arg_name=parameter.name) elm.p_types = p_type_dict[parameter] # raise ValueError('parameter {} not story element'.format(parameter.name)) decomp.elements.add(elm) return
def nested_lit(status, parent, formula, elements, edges, lit_name, relationship, lit_relationship): _lit = Literal(name=lit_name, num_args=2, truth=status) edges.add(Edge(parent, _lit, relationship)) person_name = formula.children[0].key.name arg = next(element for element in elements if person_name == element.arg_name) edges.add(Edge(_lit, arg, GC.ARGLABELS[0])) elements.add(_lit) symb_ = formula.children[1] if symb_.key == 'not': symb_ = next(iter(formula.children)) return makeLit(symb_, _lit, lit_relationship, elements, edges, False) else: return makeLit(symb_, _lit, lit_relationship, elements, edges, True)
def litFromArg(arg, DG): neg = True if arg.key == 'not': neg = False arg = arg.children[0] # arg 2 is written out lit_name = arg.key lit_elm = Literal(name=lit_name, arg_name=lit_name + str(uuid4())[19:23], num_args=len(arg.children), truth=neg) for i, ch in enumerate(arg.children): e_i = whichElm(ch.key.name, DG) DG.edges.add(Edge(lit_elm, e_i, i)) return lit_elm
def build_literal(literal, schema): predicate = literal.key # base case - its a var! if type(predicate) is not str: arg = get_arg_from_op(predicate, schema) return arg if len(literal.children) == 0 and predicate != '-': arg = get_arg_from_op_with_string(literal.key, schema) if arg is not None: return arg # return arg if hasattr(schema, "constants"): # pass if predicate in schema.constants.keys(): arg = schema.constants[predicate] return arg # recursive case - it's not a var! term_list = [] for child in literal.children: term = build_literal(child, schema) if term is None: continue term_list.append(term) # check negate and remove link as needed if len(term_list) == 1 and predicate == "not": lit = term_list[0] # special rules for non-equality constraints if lit.name in {'equals', '=', 'equal'}: compile_nonequality(lit, schema) return None lit.truth = False return lit lit = Literal(name=predicate, num_args=len(term_list), truth=True) schema.elements.add(lit) for i, term in enumerate(term_list): schema.edges.add(Edge(lit, term, i)) return lit
def makeLit(formula, parent, relationship, elements, edges, bit=None, noAdd=None): if bit == None: bit = True if noAdd == None: noAdd = False num_children = len(formula.children) lit = Literal(name=formula.key, num_args=num_children, truth=bit) if not noAdd: elements.add(lit) edges.add(Edge(parent, lit, relationship)) return lit, formula
def convert_params(params, obj_types): args = [] for i, parameter in enumerate(params): ptype = parameter.types[0] ptypes = [ptype] + obj_types[ptype] # if it's a step-typed variable... if "step" in ptypes: arg = Operator(typ=ptype, stepnumber=-1, arg_name=parameter.name) elif "literal" in ptypes: arg = Literal(typ=ptype, arg_name=parameter.name, ptypes=ptypes) elif "person" in ptypes or "character" in ptypes or "actor" in ptypes: arg = Actor(typ=ptype, arg_name=parameter.name, ptypes=ptypes) else: arg = Argument(typ=ptype, arg_name=parameter.name, ptypes=ptypes) args.append(arg) return args
def __init__(self, ID=None, type_graph=None, name=None, Elements=None, root_element=None, Edges=None, Restrictions=None): if type_graph is None: type_graph = 'Condition' if ID is None: ID = root_element.ID if root_element is None: root_element = Literal() if Elements is None: Elements = {root_element} if name is None: name = root_element.name super(Condition, self).__init__(ID, type_graph, name, Elements, root_element, Edges, Restrictions) self.replaced_ID = root_element.replaced_ID
def problemToGraphs(problem): """ Returns a dictionary: Keys: 'arg', 'init', 'goal' Values: arg dictionary, (elements, edges), (elements, edges) """ Args = { object.name: Argument(name=object.name, typ=object.typeName) for object in problem.objects if not object.typeName.lower() in {'character', 'actor', 'person', 'agent'} } Args.update({ object.name: Actor(typ=object.typeName.lower(), name=object.name) for object in problem.objects if object.typeName.lower() in {'character', 'actor', 'person', 'agent'} }) goal_elements, goal_edges = getGoalSet(problem.goal.formula, Args) goal_op = Operator(name='dummy_goal', stepnumber=1, num_args=0) goal_graph = Action(name='dummy_goal', root_element=goal_op) goal_graph.elements.update(goal_elements) goal_graph.edges.update(goal_edges) goal_graph.edges.update({ Edge(goal_op, goal_lit, 'precond-of') for goal_lit in goal_elements if type(goal_lit) is Literal }) init_op = Operator(name='dummy_init', stepnumber=0, num_args=0) init_graph = Action(name='dummy_init', root_element=init_op) for condition in problem.init.predicates: lit = Literal(name=condition.name, num_args=len(condition.parameters), truth=True) init_graph.elements.add(lit) init_graph.edges.add(Edge(init_op, lit, 'effect-of')) for i, p in enumerate(condition.parameters): init_graph.edges.add(Edge(lit, Args[p], i)) return Args, init_graph, goal_graph
def addNegativeInitStates(predicates, initAction, objects): init_tups = defaultdict(set) effects = initAction.getNeighbors(initAction.root) for eff in effects: nontup = sorted([(edge.sink, edge.label) for edge in initAction.getIncidentEdges(eff)], key=lambda x: x[1]) init_tups[eff.name].add(tuple(nontup[i][0] for i in range(len(nontup)))) objs_by_type_dict = defaultdict(set) for obj in objects: objs_by_type_dict[obj.typ].add(obj) for p in predicates: param_object_pairs = [[ obj for obj in objs_by_type_dict[param.types[0]] ] for param in p.parameters if not p.parameters[0].types is None] param_tuples = {i for i in itertools.product(*param_object_pairs)} pred = Literal(name=p.name, arg_name='init_effect', num_args=len(p.parameters), truth=False) for pt in param_tuples: if pt in init_tups[p.name]: continue pc = copy.deepcopy(pred) pc.ID = uuid4() for i, arg in enumerate(pt): initAction.edges.add(Edge(pc, arg, i)) if len(pt) > 0: initAction.elements.add(pc) initAction.edges.add(Edge(initAction.root, pc, 'effect-of'))
def decorateElm(child, DG): if child.key == 'name': elm = whichElm(child.children[0].key.name, DG) elm.name = child.children[1].key elif child.key == 'nth-step-arg' or child.key == 'nth-lit-arg': args = child.children label = int(args[0].key) parent_elm = whichElm(args[1].key.name, DG) child_elm = whichElm(args[2].key.name, DG) DG.edges.add(Edge(parent_elm, child_elm, label)) elif child.key == 'includes': arg1, arg2 = child.children DG.edges.add( Edge(whichElm(arg1.key.name, DG), whichElm(arg2.key.name, DG), 'arg-of')) elif child.key == 'truth': lit, value = child.children lit = whichElm(lit.key.name, DG) if value.key in {'t', '1', 'true', 'yes', 'y'}: lit.truth = True else: lit.truth = False elif child.key == 'effect' or child.key == 'precond': label = child.key + '-of' arg1, arg2 = child.children if len(arg2.children) > 0: child_elm = litFromArg(arg2, DG) else: child_elm = whichElm(arg2.key.name, DG) DG.edges.add(Edge(whichElm(arg1.key.name, DG), child_elm, label)) elif child.key == 'linked': arg1, arg2 = child.children dep = Literal(arg_name='link-condition' + str(uuid4())[19:23]) Src = whichElm(arg1.key.name, DG) Snk = whichElm(arg2.key.name, DG) DG.CausalLinkGraph.addEdge(Src, Snk, dep) DG.edges.add(Edge(Snk, dep, 'precond-of')) DG.edges.add(Edge(Src, dep, 'effect-of')) elif child.key == '<': arg1, arg2 = child.children DG.OrderingGraph.addEdge(whichElm(arg1.key.name, DG), whichElm(arg2.key.name, DG)) elif child.key == 'linked-by': src, snk, by = child.children try: dep = whichElm(by.key.name, DG) except: dep = litFromArg(by, DG) Src = whichElm(src.key.name, DG) Snk = whichElm(snk.key.name, DG) DG.CausalLinkGraph.addEdge(Src, Snk, dep) DG.edges.add(Edge(Snk, dep, 'precond-of')) DG.edges.add(Edge(Src, dep, 'effect-of')) elif child.key == 'consents': arg1, arg2, by = child.children DG.edges.add(Edge(whichElm(arg1.key.name, arg2.key.name, 'actor-of'))) elif child.key in {'occurs', '=', 'is', 'equals'}: # then, first argument is step element name and second argument is an operator with children args stepFromArg(child, DG) elif child.key == 'is-state': litFromArg(child, DG) else: raise NameError( 'No definition implemented for decomp predicate {}'.format( child.key))
def addNegativeInitStates(formulae, initAction, init_effects, objects, obj_types): """ for each predicate, satisfy arguments with objects. if literal not in initial state, add negation """ # collect initial states as tuples ie_args_collection = [ Condition.subgraph(initAction, init_eff.sink) for init_eff in init_effects ] # for init_eff in init_effects: # ie = Condition.subgraph(initAction, init_eff.sink) # ie_args # ie.updateArgs() # # ie_args = tuple([ie.name] + [arg.name for arg in ie.Args]) # ie_args_collection.append(ie_args) # for each predicate formula in domain for f, p in formulae: if f.key in [ "distance-between", "arg", "less-than", "play", "play-seg", "alu", "fol", "dur", "=", "obs-seg", "bel-alu", "obs-alu", "obs-seg-alu", "obs", "obs-seg-cntg", "cntg", "effect", "precond", "type", "linked", "linked-by", "<", "has-scale", "has-angle", "has-fov", "has-orient", "preconds" ]: continue # create a predicate schema template # if it's a step element or a plan element, then we need to consider all literal arguments literal_template = Condition( root_element=Literal(name=f.key, num_args=len(p.parameters))) # get consistent-typed object signatures cndts = [[obj for obj in objects if pchild.types[0] in obj.p_types] for pchild in p.parameters] # create tokens for variables in template for i, p_arg, in enumerate(p.parameters): if p_arg.types[0] == "person": arg_token = Actor(arg_name=p_arg.name, typ=p_arg.types[0]) else: arg_token = Argument(arg_name=p_arg.name, typ=p_arg.types[0]) literal_template.edges.add( Edge(literal_template.root, arg_token, i)) literal_template.elements.add(arg_token) param_tuples = [i for i in itertools.product(*cndts)] # for each candidate signature for pt in param_tuples: # create negative literal to add as negative initial step effect literal_template_copy = literal_template.deepcopy() # lit = build_literal(f, initAction) # literal_template_copy = Condition(root_element=Literal(name=f.key, num_args=len(p.parameters))) build_literal(f, literal_template_copy) literal_template_copy.root.truth = True literal_template_copy.root.ID = uuid4() literal_template_copy.elements = set( list(literal_template_copy.elements)) literal_template_copy.edges = set(list( literal_template_copy.edges)) literal_template_copy.updateArgs() # swap arguments of template literal_template_copy.replaceArgs(pt) in_initial_state = False for ie in ie_args_collection: if ie.name != literal_template_copy.name: continue if ie.truth != literal_template_copy.truth: continue if len(ie.Args) != len(literal_template_copy.Args): continue if not has_equal_args(ie.Args, literal_template_copy.Args, ie, literal_template_copy): continue in_initial_state = True if in_initial_state: continue # ignore if discovered in initial state # ie = tuple([f.key] + [t.name for t in list(pt)]) # if ie in ie_args_collection: # continue # now set it false literal_template_copy.root.truth = False # update initial Action print("building ground literal\t{}".format(literal_template_copy)) initAction.elements.update(list(literal_template_copy.elements)) initAction.edges.update(list(literal_template_copy.edges)) initAction.edges.add( Edge(initAction.root, literal_template_copy.root, 'effect-of'))
def compile_decomp_literal(literal, dschema, op_graphs): c = Condition.subgraph(dschema, literal) if literal.name == "=": if not literal.truth: print("pbreak") build_op_from_arg(c, dschema) elif literal.name == "<": src = get_arg_from_arg_name(c.Args[0].arg_name, dschema) snk = get_arg_from_arg_name(c.Args[1].arg_name, dschema) dschema.OrderingGraph.addEdge(src, snk) elif literal.name == "linked-by": src = get_arg_from_arg_name(c.Args[0].arg_name, dschema) snk = get_arg_from_arg_name(c.Args[1].arg_name, dschema) link_condition = Condition.subgraph(dschema, c.Args[2]) if link_condition.root.arg_name is None: link_condition.root.arg_name = 'lc-' + str(uuid4())[19:23] dschema.CausalLinkGraph.addEdge(src, snk, link_condition) dschema.edges.add(Edge(c.Args[0], link_condition.root, "effect-of")) dschema.edges.add(Edge(c.Args[1], link_condition.root, "precond-of")) elif literal.name == "linked": src = get_arg_from_arg_name(c.Args[0].arg_name, dschema) snk = get_arg_from_arg_name(c.Args[1].arg_name, dschema) link_condition = Condition(root_element=Literal(arg_name='lc-' + str(uuid4())[19:23])) dschema.elements.add(link_condition.root) dschema.edges.add(Edge(c.Args[0], link_condition.root, "effect-of")) dschema.edges.add(Edge(c.Args[1], link_condition.root, "precond-of")) dschema.CausalLinkGraph.addEdge(src, snk, link_condition) elif literal.name == "type": step_var = get_arg_from_arg_name(c.Args[0].arg_name, dschema) step_var.name = c.Args[1].name # swap_var_for_schema(c.Args[1].name, step_var, dschema, op_graphs) elif literal.name == "not-occurs": pass elif literal.name == "master-shot": pass elif literal.name == "has-scale": """ [note] if no argument is type scale, then raise TypeError. [note] must have declared type already (there is no special edge type called scale) """ if c.Args[0].name is None: raise ValueError( "need to declare operator type of step-typed variable with \'type\' predicate, {}" .format(literal)) schema_template = get_op_from_op_name(c.Args[0].name, op_graphs) args_with_scale = [ i for i, arg in enumerate(schema_template.Args) if arg.typ == "scale" ] if len(args_with_scale) > 1: raise ValueError('too many args typed as scale') if len(args_with_scale) == 0: raise ValueError("no args in type {} that are scale typed".format( c.Args[0].name)) arg_num = args_with_scale[0] dschema.edges.add(Edge(c.Args[0], c.Args[1], arg_num)) elif literal.name == "has-orient": if c.Args[0].name is None: raise ValueError( "need to declare operator type of step-typed variable with \'type\' predicate, {}" .format(literal)) schema_template = get_op_from_op_name(c.Args[0].name, op_graphs) args_with_ort = [ i for i, arg in enumerate(schema_template.Args) if arg.typ == "orient" ] if len(args_with_ort) > 1: raise ValueError('too many args typed as orient') if len(args_with_ort) == 0: raise ValueError("no args in type {} that are orient typed".format( c.Args[0].name)) arg_num = args_with_ort[0] dschema.edges.add(Edge(c.Args[0], c.Args[1], arg_num)) elif literal.name == "effect": dschema.edges.add(Edge(c.Args[0], c.Args[1], "effect-of")) elif literal.name == "precond": dschema.edges.add(Edge(c.Args[0], c.Args[1], "precond-of")) elif literal.name == "arg": """ e.g. (arg 0 ?est ?n0) (arg 1 ?est mid) <-- literal only here if it is a name """ arg_num = int(c.Args[0].name) step_var = c.Args[1] if type(c.Args[2]) == "Literal": step_var_operator_name = c.Args[1].name schema_template = get_op_from_op_name(step_var_operator_name, op_graphs) arg_template = schema_template.Args[arg_num] arg = arg_template.deepcopy() arg.name = c.Args[2].name dschema.elements.add(arg) dschema.edges.add(Edge(step_var, arg, arg_num)) else: dschema.edges.add(Edge(step_var, c.Args[2], arg_num)) elif literal.name == "play" or literal.name == "play-seg": pass elif literal.name == "truth": c.Args[0].truth = bool(int(c.Args[1].name)) elif literal.name == "cntg": dschema.OrderingGraph.addCntg(c.Args[0], c.Args[1]) else: raise ValueError("unknown predicate type\t{}".format(literal.name)) debug = str(literal.name) + "\t[" + ", ".join([ str(a.arg_name) if a.arg_name is not None else str(c) for a in c.Args ]) + "]" print("processing decomp literal\t{}".format(debug))