walidazizi / rdflib

Automatically exported from code.google.com/p/rdflib
Other
0 stars 0 forks source link

Suggested method on Graph for BNode Closure #132

Open GoogleCodeExporter opened 8 years ago

GoogleCodeExporter commented 8 years ago
    def bnc(self, triple, *av, **kw):
        """                                                                                                                   
        Return the BNode closure(s) for triples that are matched                                                              
        by the given "triple". Any additional positional or keyword                                                           
        arguments are passed to the constructor for the new graph.                                                            
        """
        result = Graph(*av, **kw)
        for s,p,o in self.triples(triple):
            result.add((s,p,o))
            if isinstance(o, BNode):
                result += self.bnc((o, None, None))
        return result

Original issue reported on code.google.com by wwai...@gmail.com on 22 Jul 2010 at 4:05

GoogleCodeExporter commented 8 years ago
Supporting methods:

    def one(self, triple):
        """
        Return one matching "triple" or "None"
        """
        for statement in self.triples(triple):
            return statement

    def exists(self, triple):
        """
        Return "True" if "triple" exists in the graph, "False" otherwise
        """
        statement = self.one(triple)
        if statement is not None:
            return True
        return False

Original comment by wwai...@gmail.com on 3 Nov 2010 at 10:36

GoogleCodeExporter commented 8 years ago
improved original function that won't loop in case of silly bnode loops (thanks 
gromgull): 

   def bnc(self, triple, *av, **kw):
        """                                                                                                                   
        Return the BNode closure(s) for triples that are matched                                                              
        by the given "triple". Any additional positional or keyword                                                           
        arguments are passed to the constructor for the new graph.                                                            
        """
        result = Graph(*av, **kw)
        for s,p,o in self.triples(triple):
            result.add((s,p,o))
            if isinstance(o, BNode) and not result.exists((o, None, None)):
                result += self.bnc((o, None, None))
        return result

Original comment by wwai...@gmail.com on 3 Nov 2010 at 10:38

GoogleCodeExporter commented 8 years ago
This code comes from:

    http://knowledgeforge.net/pdw/ordf/file/tip/ordf/graph.py

Original comment by wwai...@gmail.com on 3 Nov 2010 at 10:43

GoogleCodeExporter commented 8 years ago
Graphs support the `in` operator, so `exists` is unnecessary, I believe.

Original comment by vfaronov on 5 Nov 2010 at 10:46

GoogleCodeExporter commented 8 years ago
one() should raise an exception instead of returning None. The functionality is 
the same either way (though the exception can include a helpful message), but 
with None, every caller is obligated to check the type of the output. 
Forgetting to do so will lead to TypeErrors later on (when someone tries to 
unpack the None value). 

'bnc' should have a descriptive name, possibly 'bnode_closure' or 
'bnode_closure_graph'. Why doesn't a subject (or predicate) bnode cause 
recursion? (None, FOAF.name, Literal("Drew")) might be the IFP that I use to 
find a person, and wouldn't bnode_closure be the right way to get the other 
triples about that person? If I'm getting the use case wrong, please revise the 
docstring to explain why only objects are checked for BNode.

Original comment by drewpca on 6 Nov 2010 at 7:28