def __init__(self, store, uri=None): AnonymousNode.__init__(self, store, uri) self.canonical = None # Set to self if this has been canonicalized self.statements = [] self._existentialVariables = Set() self._universalVariables = Set() self.stayOpen = 0 # If set, works as a knowledegbase, never canonicalized. self._redirections = {} # Used for equalities
def evaluateObject(self, subj): ret = None for m in subj: if ret is None: ret = Set(m) else: ret.intersection_update(m) if ret is None: return Set() return ret
def evalSubj(self, obj, queue, bindings, proof, query): #really slow. Return every list I know anything about. Should I do this at all? retVals = Set([self.store.nil]) retValCopy = Set() n = 0 while retVals != retValCopy: print n, retVals, retValCopy n += 1 retValCopy = retVals.copy() for node in retValCopy: retVals.update(node._prec.values()) a = query.workingContext.occurringIn(retVals) ## Really slow. Need to generate this on the fly? print 'a=', a return a
def __init__(self, outFp, thisURI=None, base=None, flags=""): RDFSink.RDFSink.__init__(self) if outFp == None: self._xwr = XMLWriter(dummyWrite, self) else: dummyEnc, dummyDec, dummyReader, encWriter = codecs.lookup('utf-8') z = encWriter(outFp) zw = z.write self._xwr = XMLWriter(zw, self) self._subj = None self._base = base self._formula = None # Where do we get this from? The outermost formula if base == None: self._base = thisURI self._thisDoc = thisURI self._flags = flags self._nodeID = {} self._nextnodeID = 0 self._docOpen = 0 # Delay doc open <rdf:RDF .. till after binds def doNothing(): pass self._toDo = doNothing self.namespace_redirections = {} self.illegals = Set() self.stack = [0]
def evaluateObject(self, subj): if len(subj) != 2: raise ValueError( 'A symmetric difference of more than two things makes no sense' ) ret = Set() for m in subj: ret.symmetric_difference_update(m) return ret
def declareUniversal(self, v, key=None): if False and key is not AnonymousUniversal: raise RuntimeError( """We have now disallowed the calling of declareUniversal. For future reference, use newUniversal """) if verbosity() > 90: progress("Declare universal:", v) if v not in self._universalVariables: self._universalVariables.add(v) if self.occurringIn(Set([self.newSymbol(v.uriref())])): raise ValueError("Internal error: declareUniversal: %s?" % v)
def occurringIn(self, vars): "Which variables in the list occur in this?" set = Set() if verbosity() > 98: progress("----occuringIn: ", ` self `) for p in PRED, SUBJ, OBJ: y = self[p] if y is self: pass else: set = set | y.occurringIn(vars) return set
def freeVariables(self): retVal = Set() for statement in self: for node in statement.spo(): retVal.update(node.freeVariables()) retVal.difference_update(self.existentials()) retVal.difference_update(self.universals()) if self.canonical: self.freeVariablesCompute = self.freeVariables self.freeVariables = lambda: retVal.copy() return retVal.copy()
def occurringIn(self, vars): "Which variables in the list occur in this?" set = Set() for s in self.statements: for p in PRED, SUBJ, OBJ: y = s[p] if y is self: pass else: set = set | y.occurringIn(vars) return set
def n3EntailedBy(pattern, kb, vars=Set([]), existentials=Set([]), bindings={}): """See Term.unify() and term.matchSet() KB is a stronger statement han other. Bindings map variables in pattern onto kb. Self n3-entails other. Criteria: Subset of self statements must match other statements. Self's exisetntials must be subset of other's Self's universals must be superset. """ if diag.chatty_flag > 99: progress("n3EntailedBy: %s entailed by %s ?" % ( ` pattern `, ` kb `)) if diag.chatty_flag > 139: progress("Pattern is %s\n\nKB is %s" % (pattern.debugString(), kb.debugString())) assert isinstance(kb, Formula), kb if pattern is kb: return [({}, None)] nbs = matchSet( Set(pattern.statements), Set(kb.statements), vars | pattern.existentials(), # | pattern.universals(), bindings) if diag.chatty_flag > 99: progress("n3EntailedBy: match result: ", ` nbs `) if nbs == []: return [] res = [] for nb, rea in nbs: # We have matched the statements, now the lists of vars. ke = Set([nb.get(e, e) for e in kb.existentials()]) ke = pattern.occurringIn(ke) #Only ones mentioned count pe = Set([nb.get(e, e) for e in pattern.existentials()]) if diag.chatty_flag > 99: progress("\tpe=%s; ke=%s" % (pe, ke)) if not ke.issubset(pe): return [] # KB must be stronger - less e's ku = Set([nb.get(v, v) for v in kb.universals()]) pu = Set([nb.get(v, v) for v in pattern.universals()]) if diag.chatty_flag > 99: progress("\tpu=%s; ku=%s" % (pu, ku)) if not pu.issubset(ku): return [] # KB stronger - more u's if diag.chatty_flag > 99: progress("n3EntailwsBy: success with ", ` nb `) res.append((nb, None)) # That works return res
def __init__(self, sink, openFormula, thisDoc, baseURI=None, flags="", why=None): self.testdata = "" if XMLLiteralsAsDomTrees: self.domImplementation = xml.dom.getDOMImplementation() self.domDocument = None self.domElement = None self.flags = flags self._stack =[] # Stack of states self._nsmap = [] # stack of namespace bindings self._prefixMap = [] self.LiteralNS = None self._delayedStatement = None self.sink = sink self._thisDoc = thisDoc if baseURI != None: self._base = baseURI else: self._base = thisDoc self._state = STATE_OUTERMOST # Maybe should ignore RDF outside <rdf:RDF>?? if sink: if openFormula==None: self._context = sink.newFormula(thisDoc + "#_formula") else: self._context = openFormula self._formula = self._context # Root formula self._genPrefix = uripath.join(thisDoc, "#_rdfxg") # allow parameter override? self.sink.setGenPrefix(self._genPrefix) self.sink.startDoc() self.merge = self.sink.newSymbol(NODE_MERGE_URI) else: self._context = None self._reason = why # Why the parser w self._reason2 = None # Why these triples if diag.tracking: self._reason2 = BecauseOfData( sink.newSymbol(thisDoc), because=self._reason) self._subject = None self._predicate = None self._datatype = None self._language = None self._nodeIDs = {} self._items = [] # for <rdf:li> containers self._litDepth = 0 self._usedIDs = Set() version = "$Id$" # self.sink.makeComment("RDF parsed by "+version[1:-1]) if "D" in self.flags: # Assume default namespace declaration if sink: self.sink.setDefaultNamespace(self._thisDoc+"#") self._nsmap = [ { "": "#"} ]
def substitution(self, bindings, why=None, cannon=False, keepOpen=False): "Return this or a version of me with subsitution made" assert isinstance(bindings, dict) store = self.store if self in bindings: return bindings[self] oc = self.occurringIn(bindings.keys()) if oc == Set(): return self # phew! y = store.newFormula() if verbosity() > 90: progress( "substitution: formula" + ` self ` + " becomes new " + ` y `, " because of ", oc) y.loadFormulaWithSubstitution(self, bindings, why=why) if keepOpen: return y return y.canonicalize(cannon=cannon)
def __init__(self, rule, bindings, knownExistentials, evidence, kb, because=None): #print rule #raise Error Reason.__init__(self) self._bindings = bindings self._rule = rule self._evidence = evidence # Set of statements etc to justify LHS self._kb = kb # The formula the rule was trusting at base self._reason = because self._existentials = knownExistentials self.statements = Set() return
def conclude(self, bindings, evidence=[], extraBNodes=Set(), allBindings=None): """When a match found in a query, add conclusions to target formula, and also remove retractions. Returns the number of statements added.""" if diag.chatty_flag > 25: progress("Insertions will now be made into %s. Bindings %s" % (self.workingContext, bindings)) result = Query.conclude(self, bindings, evidence) # delete statements if diag.chatty_flag > 25: progress( "Insertions made, deletions will now be made. Bindings %s" % bindings) for st in self.retraction: s, p, o = st.spo() subj = self.doSubst(s, bindings) pred = self.doSubst(p, bindings) obj = self.doSubst(o, bindings) ss = self.workingContext.statementsMatching(subj=subj, pred=pred, obj=obj) if len(ss) != 1: progress("""Error: %i matches removing statement {%s %s %s} bound as {%s %s %s} from %s:\n%s\n""" % (len(ss), s, p, o, subj.uriref(), pred.uriref(), obj.uriref(), self.workingContext, ss)) progress(self.workingContext.debugString()) raise RuntimeError( """Error: %i matches removing statement {%s %s %s} bound as {%s %s %s} from %s""" % (len(ss), s, p, o, ` subj `, pred.uriref(), ` obj `, self.workingContext)) if diag.chatty_flag > 25: progress("Deleting %s" % ss[0]) self.workingContext.removeStatement(ss[0]) self.justOne = 1 # drop out of here when done return 1 # Success -- behave as a test and drop out
def findLegal(dict, str): ns = Set(dict.values()) s = u'' k = len(str) while k and str[k - 1] not in string.ascii_letters: k = k - 1 i = k while i: if str[i - 1] not in string.ascii_letters: break i = i - 1 j = i # raise RuntimeError(str[:i]+'[i]'+str[i:k]+'[k]'+str[k:]) while j < k and (str[j:k] in ns or str[j:k][:3] == 'xml'): j = j + 1 if j == k: # we need to find a better string s = str[i:k] while s in ns or s[:3] == 'xml': s = choice(string.ascii_letters) + s[:-1] return s else: return str[j:k]
def evaluateObject(self, subj): # if isNonEmptyListTerm(subj): subj = listify(subj) return Set(subj)
"""A series of functions to test if a string is a valid qName $ ID: $ """ import string #from unicodedata import category from set_importer import Set LETTER_CATEGORIES = Set(["Ll", "Lu", "Lo", "Lt", "Nl"]) NCNAME_CATEGORIES = LETTER_CATEGORIES.union(Set(["Mc", "Me", "Mn", "Lm", "Nd"])) NCNameChar, NCNameStartChar, NameStartChar, NameChar, \ Letter, Digit, CombiningChar, Extender, BaseChar, Ideographic = \ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 def isXMLChar10(character, char_class): """Is this a valid <char_class> character char_class is one of NCNameChar, NCNameStartChar, NameStartChar, NameChar, Letter, Digit, CombiningChar, Extender, BaseChar, Ideographic usual use is isXMLChar(character, isXML.NCNameChar) """ num = ord(character) character = unicode(character) if char_class == Letter:
def patch(workingContext, patchFormula): """A task of running a set of updates on a knowledge base This is simpler than an Inference task, in that a patch is only done once, patches cannot lead to new patches, etc. """ if diag.chatty_flag > 20: progress("New Update task, patches from %s applied to %s" % (patchFormula, workingContext)) store = workingContext.store true = store.newFormula().close() # {} universals = Set() lhs_done = [] agenda = {} for pred in store.insertion, store.deletion: for s in patchFormula.statementsMatching(pred=pred): dict = agenda.get(s.subject(), None) if dict == None: dict = {store.insertion: [], store.deletion: []} agenda[s.subject()] = dict dict[pred].append(s.object()) for lhs, dict in sorted(agenda.items()): if diag.chatty_flag > 19: progress("Patches lhs= %s: %s" % (lhs, dict)) if isinstance(lhs, Formula): if lhs.universals() != Set(): raise RuntimeError( """Cannot query for universally quantified things. As of 2003/07/28 forAll x ...x cannot be on left hand side of rule. This/these were: %s\n""" % lhs.universals()) addenda, minuenda = dict[store.insertion], dict[store.deletion] while addenda or minuenda: if addenda: conclusion = addenda.pop() else: conclusion = true if minuenda: retraction = minuenda.pop() else: retraction = true unmatched = lhs.statements[:] templateExistentials = lhs.existentials().copy() _substitute({lhs: workingContext}, unmatched) # Change context column variablesMentioned = lhs.occurringIn(patchFormula.universals()) variablesUsed = conclusion.occurringIn(variablesMentioned) | \ retraction.occurringIn(variablesMentioned) for x in sorted(variablesMentioned): if x not in variablesUsed: templateExistentials.add(x) if diag.chatty_flag > 20: progress("New Patch =========== applied to %s" % (workingContext)) for s in lhs.statements: progress(" ", ` s `) progress("+=>") for s in conclusion.statements: progress(" ", ` s `) progress("-=>") for s in retraction.statements: progress(" ", ` s `) progress("Universals declared in outer " + seqToString(patchFormula.universals())) progress(" mentioned in template " + seqToString(variablesMentioned)) progress(" also used in conclusion " + seqToString(variablesUsed)) progress("Existentials in template " + seqToString(templateExistentials)) q = UpdateQuery(store, unmatched=unmatched, template=lhs, variables=patchFormula.universals(), existentials=templateExistentials, workingContext=workingContext, conclusion=conclusion, retraction=retraction, rule=None) q.resolve()
def evaluateObject(self, subj): return Set(subj)
def evaluateObject(self, subj): ret = Set() for m in subj: ret.update(m) return ret
def evaluateSubject(self, obj): return Set(obj)
def __init__(self, source, because=None): Reason.__init__(self) self._source = source self._reason = because self.statements = Set() return
def flatten(formula): """Flatten a formula This will minimally change a formula to make it valid RDF flattening a flattened formula should thus be the unity """ why = None store = formula.store valid_triples = formula.statements[:] for triple in valid_triples: for part in SUBJ, PRED, OBJ: try: triple[part] = triple[part].close() except AttributeError: pass invalid_triples = [] new_invalid_triples = [] shared_vars = Set() for triple in valid_triples: if triple.occurringIn(formula.universals()): new_invalid_triples.append(triple) shared_vars.update(triple.occurringIn(formula.existentials())) for triple in new_invalid_triples: try: valid_triples.remove(triple) except ValueError: pass while new_invalid_triples: invalid_triples.extend(new_invalid_triples) new_invalid_triples = [] for triple in valid_triples: if triple.occurringIn(shared_vars): new_invalid_triples.append(triple) shared_vars.update(triple.occurringIn(formula.existentials())) for triple in new_invalid_triples: try: valid_triples.remove(triple) except ValueError: pass still_needed_existentials = reduce( Set.union, [x.occurringIn(formula.existentials()) for x in valid_triples], Set()) returnFormula = formula.newFormula() tempBindings = {} bNodeBindings = {} for a in still_needed_existentials: bNodeBindings = returnFormula.newBlankNode(a) tempformula = formula.newFormula() for var in formula.universals(): tempBindings[var] = tempformula.newUniversal(var) for var in formula.existentials(): termBindings[var] = tempformula.newBlankNode(var) for triple in invalid_triples: tempformula.add(triple[SUBJ].substitution(tempBindings, why=why), triple[PRED].substitution(tempBindings, why=why), triple[OBJ].substitution(tempBindings, why=why)) #now for the stuff that isn't reified for triple in valid_triples: returnFormula.add( triple[SUBJ].substitution(bNodeBindings, why=why).flatten(returnFormula), triple[PRED].substitution(bNodeBindings, why=why).flatten(returnFormula), triple[OBJ].substitution(bNodeBindings, why=why).flatten(returnFormula)) if tempformula.statements != []: x = tempformula.reification(returnFormula) returnFormula.add(x, store.type, store.Truth) return returnFormula.close()
def __init__(self, str, because=None): Reason.__init__(self) self._string = str self._reason = because self.statements = Set() return
def __init__(self, f, set): raise RuntimeError(f, set) KBReasonTracker.__init__(self, f) self.fodder = Set()