R.P.O.D.
R.P.O.D.

Reputation: 81

python rdflib transitive query

I am fairly new with using rdflib and my problem is rather simple. I have several n-triple files containing a quite considerate amount of data, while each file has the same domain in their subject, the domain in the object is different for each file. Now I want to input one, or more, files and compare them with every other file in the dataset to get the triples that contain the same subject:

[selected file]
a owl:sameAs b

[other files]
a owl:sameAs c
a owl:sameAs d

Should result in the output:

b owl:sameAs c
b owl:sameAs d

My current approach is very naive and takes too long, as I iterate through all triples in the selected file it checks for every other triple if it contains the same subject and predicate.

...
for mainGraph in mainGraphs:
    for s,p,o in mainGraph:
        for graph in graphs:
            for s1,p1,o1 in graph:
                if s == s1 and p == p1:
                    backlinks.add( (o, OWL.sameAs, o1) )
...

I tried to insert a SPARQL query, which didn't work either:

...
for mainGraph in mainGraphs:
    for graph in graphs:
        union = mainGraph + graph 
        qres = union.query(
        """SELECT DISTINCT ?x ?y
            WHERE
            {
              ?x owl:sameAs+ ?y .
            }""")
...

My question is if there is a faster and simpler way which would do the same thing.

Any help would be much appreciated.

Upvotes: 1

Views: 427

Answers (1)

R.P.O.D.
R.P.O.D.

Reputation: 81

After checking more of the rdflib documentation I figured out the following solution:

...
for mainGraph in mainGraphs:
    for s,p,o in mainGraph.triples( (None, OWL.sameAs, None) ):
        for graph in graphs:
            for s1,p1,o1 in graph.triples( (s,p,None) ):
                backlinks.add( (o1, OWL.sameAs, o) )
...

It is considerably faster. If someone has a faster solution I would greatly appreciate it if they would post it.

Upvotes: 2

Related Questions