Virtuoso SPARQL can use an inference context for inferring triples that are not physically stored. This functionality applies to physically stored quads and not to virtual triples generated from relational data with RDF views. Such an inference context can be built from one or more graphs containing RDF Schema triples. The supported RDF Schema or OWL constraints are imported from these graphs and are grouped together into rule bases. A rule base is a persistent entity that can be referenced by a SPARQL query or end point. Queries running with a given rule base work as if the triples asserted by this rule base were included in the graph or graphs accessed by the query.
As of version 5.0, Virtuoso recognizes rdfs:subClassOf and rdfs:subPropertyOf. owl:sameAs is considered for arbitrary subjects and objects if specially enabled by a pragme in the query. As of 5.00.3031, owl:sameAs, owl:equivalentClass and owl:equivalentProperty are also considered when determining subclass or subproperty relations. If two classes are equivalent, they share all instances, subclasses and superclasses directly or indirectly stated in the data for either class. Other RDF Schema or OWL information is not taken into account.
Since RDF Schema and OWL schemas are RDF graphs, these can be loaded into the triple store. Thus, in order to use such a schema as query context, one first loads the corresponding document into the triple store using ttlp or rdf_load_rdfxml or related functions. After the schema document is loaded, one can add the assertions therein into an inference context with the rdfs_rule_set function. This function specifies a logical name for the rule set plus a graph URI. It is possible to combine multiple schema graphs into a single rule set. A single schema graph may also independently participate in multiple rule sets.
rdfs_rule_set (in name varchar, in uri varchar, in remove int := 0)
This function adds the applicable facts of the graph into a rule set. The graph URI must correspond to the graph IRI of a graph stored in the triple store of the Virtuoso instance. If the remove argument is true, the specified graph is removed from the rule set instead.
Changing a rule set affects queries made after the change. Some queries may have been previously compiled and will not be changed as a result of modifying the rule set. When a rule set is changed, i.e. when rdfs_rule_set is called with the first argument set to a pre-existing rule set's name, all the graphs associated with this name are read and the relevant facts are added to a new empty rule set. Thus, if triples are deleted from or added to the graphs comprising the rule set, calling rdfs_rule_set will refresh the rule set to correspond to the state of the stored graphs.
Virtuoso SPARQL supports RDF Schema subclasses and subproperties.
The predicates rdfs:subClassOf and rdfs:subPropertyOf are recognized when they appear in graphs included in a rule set. When such a rule set is specified as a context for a SPARQL query, the following extra triples are generated as needed.
For every ?s rdf:type ?class, a triple ?s rdf:type ?superclass is considered to exist, such that ?superclass is a direct or indirect superclass of ?class. Direct superclasses are declared with the rdfs:subClassOf predicate in the rule set graph. Transitivity of superclasses is automatically taken into account, meaning that if a is a superclass of b and b a superclass of c, then a is a superclass of c also. Cyclic superclass relations are not allowed. If such occur in the rule set data, the behavior is undefined but will not involve unterminating recursion.
For every ?s ?subpredicate ?o, a triple ?s ?superpredicate ?o is considered to exist if the rule context declares ?superpredicate to be a superpredicate of ?predicate. This is done by having the triple ?subpredicate rdfs:subPropertyOf ?superpredicate as part of the graphs making up the rule context. Transitivity is observed, thus if a is a subpredicate of b and b a subpredicate of c, then a is also a subpredicate of c.
Virtuoso has limited support for the OWL same-as predicate.
In the following, the abbreviation owl:sameAs is used for the IRI http://www.w3.org/2002/07/owl#same-as .
If same-as traversal is enabled and a triple pattern with a given subject or object is being matched, all the synonyms of the S and O will be tried and results generated for all the tried bindings of S and O. The set of synonyms is generated at run time by following all owl:sameAs triples where the IRI in question is either the subject or the object. These are followed recursively from object to subject and subject to object until the complete transitive closure is generated. All same-as triples from all the graphs applicable to instantiating the triple pattern at hand are considered.
Thus, if we have
<thing> <owl:sameAs> <gizmo> . <thing> <label> "thingy" .
and we instantiate ?s <label> "thingy" we get ?s bound to <thing>.
If we instantiate <gizmo> <label> ?l we get ?l bound to "thingy" because the subject was given and it was expanded to its synonyms.
If binding a variable in a pattern where the variable was free, we do not expand the value to the complete set of its synonyms.
Same-as expansion is enabled in a query by define input:same-as "yes" in the beginning of the SPARQL query. This has a significant run time cost but is in some cases useful when joining data between sets which are mapped to each other with same-as.
We note that the number of same-as expansions will depend on the join order used for the SPARQL query. The compiler does not know the number of synonyms and cannot set the join order accordingly. Regardless of the join order we will however get at least one IRI of the each synonym set as answer. Also when interactively navigating a graph with a browser, the same-as expansion will take all synonyms into account.
For getting the complete entailment of same-as, a forward chaining approach should be used, effectively asserting all the implied triples.
Triples entailed by subclass or subproperty statements in an inference context are not physically stored. Such triples are added to the result set by the query run time as needed. Also queries involving subclass or subproperty rules are not rewritten into unions of all the possible triple patterns that might imply the pattern that is requested. Instead, the SQL compiler adds special nodes that iterate over subclasses or subproperties at run time. The cost model also takes subclasses and subproperties into account when determining the approximate cardinality of triple patterns.
In essence, Virtuoso's support for subclasses and subproperties is backward chaining, i.e. it does not materialize all implied triples but rather looks for the basic facts implying these triples at query evaluation time.
In a SPARQL query, the define input:inference clause is used to instruct the compiler to use the rules in the named rule set. For example:
SQL> rdfs_rule_set ('sample', 'rule_graph');
SQL> sparql define input:inference "sample" select * from <g> where {?s ?p ?o};
will include all the implied triples in the result set, using the rules in the sample rule set.
Inference can be enabled triple pattern by triple pattern. This is done with the option (inference 'rule_set') clause after the triple pattern concerned. Specifying option (inference none) will disable inference for the pattern concerned while the default inference context applies to the rest of the patterns. Note that the keyword is input:inference in the query header and simply inference in the option clause. See the examples section below for examples.
In SQL, if RDF_QUAD occurs in a select from clause, inference can be added with the table option WITH, as follows:
select * from rdf_quad table option (with 'sample') where g = iri_to_id ('xx', 0);
This is about the same as:
define input:inference "sample" select * from <xx> where {?s ?p ?o}
ttlp ('
<http://localhost:8890/dataspace> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://rdfs.org/sioc/ns#Space>.
<http://localhost:8890/dataspace/test2/weblog/test2tWeblog> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://rdfs.org/sioc/types#Weblog> .
<http://localhost:8890/dataspace/discussion/oWiki-test1Wiki> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://rdfs.org/sioc/types#MessageBoard>.
<http://localhost:8890/dataspace> <http://rdfs.org/sioc/ns#link> <http://localhost:8890/ods> .
<http://localhost:8890/dataspace/test2/weblog/test2tWeblog> <http://rdfs.org/sioc/ns#link> <http://localhost:8890/dataspace/test2/weblog/test2tWeblog>.
<http://localhost:8890/dataspace/discussion/oWiki-test1Wiki> <http://rdfs.org/sioc/ns#link> <http://localhost:8890/dataspace/discussion/oWiki-test1Wiki> .
', '', 'http://localhost:8890/test');
This loads data space instance data Triples into a Named Graph: <http://localhost:8890/test>
ttlp (' @prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
<http://rdfs.org/sioc/ns#Space> rdfs:subClassOf <http://www.w3.org/2000/01/rdf-schema#Resource> .
<http://rdfs.org/sioc/ns#Container> rdfs:subClassOf <http://rdfs.org/sioc/ns#Space> .
<http://rdfs.org/sioc/ns#Forum> rdfs:subClassOf <http://rdfs.org/sioc/ns#Container> .
<http://rdfs.org/sioc/types#Weblog> rdfs:subClassOf <http://rdfs.org/sioc/ns#Forum> .
<http://rdfs.org/sioc/types#MessageBoard> rdfs:subClassOf <http://rdfs.org/sioc/ns#Forum> .
<http://rdfs.org/sioc/ns#link> rdfs:subPropertyOf <http://rdfs.org/sioc/ns> .
', '', 'http://localhost:8890/schema/test');
This loads a Triples into a Named Graph for schema/ontology data called: <http://localhost:8890/schema/test> that expresses assertions about subclasses and subproperties.
rdfs_rule_set ('http://localhost:8890/schema/property_rules1', 'http://localhost:8890/schema/test');
This defines the rule context http://localhost:8890/schema/property_rules1 that is initialized from the contents of graph http://localhost:8890/schema/test.
SQL>sparql define input:inference 'http://localhost:8890/schema/property_rules1' select ?s from <http://localhost:8890/test> where {?s <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://rdfs.org/sioc/ns#Space> };
s
VARCHAR
_______________________________________________________________________________
http://localhost:8890/dataspace/test2/weblog/test2tWeblog
http://localhost:8890/dataspace/discussion/oWiki-test1Wiki
http://localhost:8890/dataspace
3 Rows. -- 0 msec.
This returns the instances of http://rdfs.org/sioc/ns#Space. Since http://rdfs.org/sioc/types#Weblog and http://rdfs.org/sioc/types#MessageBoard are subclasses of http://rdfs.org/sioc/ns#Space, instances of http://rdfs.org/sioc/ns#Space, http://rdfs.org/sioc/types#Weblog and http://rdfs.org/sioc/types#MessageBoard are all returned. This results in the subjects http://localhost:8890/dataspace, http://localhost:8890/dataspace/test2/weblog/test2tWeblog and http://localhost:8890/dataspace/discussion/oWiki-test1Wiki.
SQL>select id_to_iri (s)
from rdf_quad table option (with 'http://localhost:8890/schema/property_rules1')
where g = iri_to_id ('http://localhost:8890/test',0)
and p = iri_to_id ('http://www.w3.org/1999/02/22-rdf-syntax-ns#type', 0)
and o = iri_to_id ('http://rdfs.org/sioc/ns#Space', 0);
callret
VARCHAR
_______________________________________________________________________________
http://localhost:8890/dataspace/test2/weblog/test2tWeblog
http://localhost:8890/dataspace/discussion/oWiki-test1Wiki
http://localhost:8890/dataspace
3 Rows. -- 10 msec.
This is the corresponding SQL query, internally generated by the SPARQL query.
Below we first look for all instances of http://rdfs.org/sioc/ns#Space with some property set to http://localhost:8890/dataspace/test2/weblog/test2tWeblog. We get the subject http://localhost:8890/dataspace/test2/weblog/test2tWeblog and the properties http://rdfs.org/sioc/ns#link and http://rdfs.org/sioc/ns. The join involves both subclass and subproperty inference. Then we turn off the inference for the second pattern and only get the property http://rdfs.org/sioc/ns#link. Then we do the same but now specify that inference should apply only to the first triple pattern.
SQL>sparql define input:inference 'http://localhost:8890/schema/property_rules1' select * from <http://localhost:8890/test>
where { ?s ?p <http://rdfs.org/sioc/ns#Space> . ?s ?p1 <http://localhost:8890/dataspace/test2/weblog/test2tWeblog> . };
s p p1
VARCHAR VARCHAR VARCHAR
_______________________________________________________________________________
http://localhost:8890/dataspace/test2/weblog/test2tWeblog http://www.w3.org/1999/02/22-rdf-syntax-ns#type http://rdfs.org/sioc/ns#link
http://localhost:8890/dataspace/test2/weblog/test2tWeblog http://www.w3.org/1999/02/22-rdf-syntax-ns#type http://rdfs.org/sioc/ns
2 Rows. -- 0 msec.
SQL>sparql select * from <http://localhost:8890/test>
where { ?s ?p <http://rdfs.org/sioc/ns#Space> option (inference 'http://localhost:8890/schema/property_rules1') . ?s ?p1 <http://localhost:8890/dataspace/test2/weblog/test2tWeblog> . };
s p p1
VARCHAR VARCHAR VARCHAR
_______________________________________________________________________________
http://localhost:8890/dataspace/test2/weblog/test2tWeblog http://www.w3.org/1999/02/22-rdf-syntax-ns#type http://rdfs.org/sioc/ns#link
1 Rows. -- 10 msec.
ttlp ('
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
<http://dbpedia.org/property/birthcity> rdfs:subPropertyOf <http://dbpedia.org/property/birthPlace> .
<http://dbpedia.org/property/birthcountry> rdfs:subPropertyOf <http://dbpedia.org/property/birthPlace> .
<http://dbpedia.org/property/cityofbirth> rdfs:subPropertyOf <http://dbpedia.org/property/birthPlace> .
<http://dbpedia.org/property/countryofbirth> rdfs:subPropertyOf <http://dbpedia.org/property/birthPlace> .
<http://dbpedia.org/property/countyofbirth> rdfs:subPropertyOf <http://dbpedia.org/property/birthPlace> .
<http://dbpedia.org/property/cityofdeath> rdfs:subPropertyOf <http://dbpedia.org/property/deathPlace> .
<http://dbpedia.org/property/countryofdeath> rdfs:subPropertyOf <http://dbpedia.org/property/deathPlace> . "",
'http://dbpedia.org/inference/rules#') ;
rdfs_rule_set ('http://dbpedia.org/schema/property_rules1', 'http://dbpedia.org/inference/rules#');
sparql
define input:inference 'http://dbpedia.org/schema/property_rules1'
prefix p: <http://dbpedia.org/property/>
select ?s from <http://dbpedia.org> where {?s p:birthcity ?o }
limit 50
s
VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/Britt_Janyk
http://dbpedia.org/resource/Chiara_Costazza
http://dbpedia.org/resource/Christoph_Gruber
http://dbpedia.org/resource/Daron_Rahlves
http://dbpedia.org/resource/Finlay_Mickel
http://dbpedia.org/resource/Genevi%C3%A8ve_Simard
http://dbpedia.org/resource/Johann_Grugger
http://dbpedia.org/resource/Kalle_Palander
http://dbpedia.org/resource/Marc_Gini
http://dbpedia.org/resource/Mario_Scheiber
http://dbpedia.org/resource/Prince_Hubertus_of_Hohenlohe-Langenburg
http://dbpedia.org/resource/Resi_Stiegler
http://dbpedia.org/resource/Steven_Nyman
http://dbpedia.org/resource/Hannes_Reichelt
http://dbpedia.org/resource/Jeremy_Transue
15 Rows. -- 167 msec.
sparql
define input:inference 'http://dbpedia.org/schema/property_rules1'
prefix p: <http://dbpedia.org/property/>
select ?s from <http://dbpedia.org> where {?s p:countryofbirth ?o }
limit 50
s
VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/A._J._Wood
http://dbpedia.org/resource/A._J._Godbolt
http://dbpedia.org/resource/Ac%C3%A1cio_Casimiro
http://dbpedia.org/resource/Adam_Fry
http://dbpedia.org/resource/Adam_Gilchrist
http://dbpedia.org/resource/Adam_Griffin
http://dbpedia.org/resource/Adam_Gross
...
50 Rows. -- 324 msec.
sparql
define input:inference 'http://dbpedia.org/schema/property_rules1'
prefix p: <http://dbpedia.org/property/>
select ?s from <http://dbpedia.org> where {?s p:countyofbirth ?o }
limit 50
s
VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/Eddie_Colman
1 Rows. -- 163 msec.
sparql
define input:inference 'http://dbpedia.org/schema/property_rules1'
prefix p: <http://dbpedia.org/property/>
select ?s from <http://dbpedia.org> where {?s p:birthPlace ?o }
s
VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/Eddie_Colman
http://dbpedia.org/resource/Jeremy_Transue
http://dbpedia.org/resource/Finlay_Mickel
http://dbpedia.org/resource/Prince_Hubertus_of_Hohenlohe-Langenburg
http://dbpedia.org/resource/Hannes_Reichelt
http://dbpedia.org/resource/Johann_Grugger
http://dbpedia.org/resource/Chiara_Costazza
...
155287 Rows. -- 342179 msec.
--- Load Class Hierarchy into a Named Graph
select ttlp_mt (file_to_string_output ('yago-class-hierarchy_en.nt'),
'', 'http://dbpedia.org/resource/classes/yago#');
-- Create an Inference Rule that references the Yago Class Hierarchy
Named Graph
SQL>rdfs_rule_set ('http://dbpedia.org/resource/inference/rules/yago#',
'http://dbpedia.org/resource/classes/yago#');
-- Query for the "The Lord of the Rings" which is a "Book" as
-- explicitly claimed in the DBpedia data set (instance data)
SQL>SPARQL
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX dbpedia: <http://dbpedia.org/property/>
PREFIX yago: <http://dbpedia.org/class/yago/>
SELECT ?s
FROM <http://dbpedia.org>
WHERE {
?s a yago:Book106410904 .
?s dbpedia:name "The Lord of the Rings"@en .
};
s
VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/The_Lord_of_the_Rings
1 Rows. -- 321 msec.
-- Query aimed at Books via query scoped to the "Publication" class
-- of which it is a subclass in the Yago Hierarchy
SQL>SPARQL
define input:inference
'http://dbpedia.org/resource/inference/rules/yago#'
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX dbpedia: <http://dbpedia.org/property/>
PREFIX yago: <http://dbpedia.org/class/yago/>
SELECT ?s
FROM <http://dbpedia.org>
WHERE {
?s a yago:Publication106589574 .
?s dbpedia:name "The Lord of the Rings"@en .
};
s
VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/The_Lord_of_the_Rings
-- # Variant of query with Virtuoso's Full Text Index extension: bif:contains
SQL>SPARQL
define input:inference
'http://dbpedia.org/resource/inference/rules/yago#'
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX dbpedia: <http://dbpedia.org/property/>
PREFIX yago: <http://dbpedia.org/class/yago/>
SELECT ?s ?n
FROM <http://dbpedia.org>
WHERE {
?s a yago:Publication106589574 .
?s dbpedia:name ?n .
?n bif:contains 'Lord and Rings'
};
s n
VARCHAR VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/The_Lord_of_the_Rings The Lord of the Rings
http://dbpedia.org/resource/Journeys_of_Frodo Journeys of Frodo: An Atlas of J. R. R. Tolkien's The Lord of the Ri
ngs
http://dbpedia.org/resource/The_Lord_of_the_Rings:_A_Reader%27s_Companion The Lord of the Rings: A Reader's Companion
http://dbpedia.org/resource/Tolkien:_A_Look_Behind_%22The_Lord_of_the_Rings%22 A Look Behind "The Lord of the Rings""
4 Rows. -- 29573 msec.
-- Retrieve all individuals instances of the Book Class
SQL>SPARQL
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX dbpedia: <http://dbpedia.org/property/>
PREFIX yago: <http://dbpedia.org/class/yago/>
SELECT ?s ?n
FROM <http://dbpedia.org>
WHERE {
?s a yago:Book106410904 .
?s dbpedia:name ?n .
}
limit 10;
s n
VARCHAR VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/.hack//AI_buster .hack// AI buster
http://dbpedia.org/resource/1000_Love_and_Sex_Quiz 1000 Love and Sex Quiz
http://dbpedia.org/resource/1491:_New_Revelations_of_the_Americas_Before_Columbus 1491: New Revelations of the Americas Before Columbus
http://dbpedia.org/resource/.hack//AI_buster_2 .hack// AI buster 2
http://dbpedia.org/resource/100_Books_by_August_Derleth 100 Books by August Derleth
http://dbpedia.org/resource/1634:_The_Baltic_War 1634: The Baltic War
http://dbpedia.org/resource/003%C2%BD:_The_Adventures_of_James_Bond_Junior 003-+: The Adventures of James Bond Junior"
http://dbpedia.org/resource/1001_Movies_You_Must_See_Before_You_Die 1001 Movies You Must See Before You Die
http://dbpedia.org/resource/1066_and_All_That 1066 and All That
http://dbpedia.org/resource/14%2C000_Things_to_be_Happy_About 14,000 Things to be Happy About
10 Rows. -- 1422 msec.
-- Retrieve all individuals instances of Publication Class which
-- should include all Books.
SQL>SPARQL
define input:inference
'http://dbpedia.org/resource/inference/rules/yago#'
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX dbpedia: <http://dbpedia.org/property/>
PREFIX yago: <http://dbpedia.org/class/yago/>
SELECT ?s ?n
FROM <http://dbpedia.org>
WHERE {
?s a yago:Publication106589574 .
?s dbpedia:name ?n .
};
s n
VARCHAR VARCHAR
_______________________________________________________________________________
http://dbpedia.org/resource/461_Ocean_Boulevard 461 Ocean Boulevard
http://dbpedia.org/resource/A_Love_Supreme A Love Supreme
http://dbpedia.org/resource/A_Night_at_Red_Rocks_with_the_Colorado_Symphony_Orchestra A Night at Red Rocks with the Colorado Symphony Orchestra
http://dbpedia.org/resource/At_Fillmore_East At Fillmore East
http://dbpedia.org/resource/August_and_Everything_After August and Everything After
...
|
Previous
RDF Views -- Mapping Relational Data to RDF |
Chapter Contents |
Next
Using Full Text Search in SPARQL |