Sparql - Conditional Output - sparql

I am very new to the semantic web and sparql. I have an internal ontology that uses SmartLogic in order to manage the data.
I am writing some simple queries to get started.
PREFIX skos: <http://www.w3.org/2004/02/skos/core#> # Simple Knowledge Organization System - https://www.w3.org/2004/02/skos/
PREFIX skosxl: <http://www.w3.org/2008/05/skos-xl#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX rdfs: <https://www.w3.org/TR/rdf-schema/>
prefix owl: <http://www.w3.org/2002/07/owl#>
prefix ap: <http://cv.ap.org/ns>
SELECT DISTINCT
?subjectPrefLabel ?p ?o ?oL
WHERE {
{
?subject skosxl:prefLabel ?subjectLabel .
?subjectLabel skosxl:literalForm ?subjectPrefLabel .
?subject ?p ?o .
OPTIONAL {?o skos:prefLabel ?oL}
}
FILTER regex(?subjectPrefLabel, "Trump", 'i')
} order by ?subjectPrefLabel
This query returns results that look like :
I am trying to merge the ?o and ?oL fields, so that it will replace the ?o field, if and only if there is a valid ?oL Field
I haven't been able to figure it out quite yet. If there is any suggestions please let me know.

A bit difficult without data for testing the query, but in SPARQL 1.1 you can use BIND(IF(condition,then,else) as ?result ):
PREFIX skosxl: <http://www.w3.org/2008/05/skos-xl#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX owl: <http://www.w3.org/2002/07/owl#>
PREFIX skos: <http://www.w3.org/2004/02/skos/core#>
PREFIX rdfs: <https://www.w3.org/TR/rdf-schema/>
PREFIX ap: <http://cv.ap.org/ns>
SELECT DISTINCT ?subjectPrefLabel ?p ?o
WHERE
{ ?subject skosxl:prefLabel ?subjectLabel .
?subjectLabel
skosxl:literalForm ?subjectPrefLabel .
?subject ?p ?o_tmp
OPTIONAL
{ ?o_tmp skos:prefLabel ?oL }
BIND(if(bound(?oL), ?oL, ?o_tmp) AS ?o)
FILTER regex(?subjectPrefLabel, "Trump", "i")
}
ORDER BY ?subjectPrefLabel

Related

Error handling of SPARQL query with given RDF graph

I have the following RDF graph with prefixes
PREFIX r: <http://dbpedia.org/resources/>
PREFIX o: <http://dbpedia.org/ontology/>
And the query
PREFIX r: <http://dbpedia.org/resources/>
PREFIX o: <http://dbpedia.org/ontology/>
SELECT ?s ?author
WHERE {
?s o:type o:Book .
?s o:author ?author .
?author ?incategory r:Category:American_atheists.
}
I am now wondering what the output would look like. I have tried using https://dbpedia.org/sparql but this results in a parsing error.
Is this a proper query anyway ?
The graph has the prefix r for Book and the query has o:Book in the triple.
The parsing error is due to the colon after r:Category. Colon in abbreviated IRIs can only be used as part of the prefix. This query should work:
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX r: <http://dbpedia.org/resource/>
PREFIX o: <http://dbpedia.org/ontology/>
SELECT ?s ?author
WHERE {
?s rdf:type o:Book .
?s o:author ?author .
?author ?incategory <http://dbpedia.org/resource/Category:American_atheists> .
}
Or, if you want a more concise WHERE clause:
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX r: <http://dbpedia.org/resource/>
PREFIX o: <http://dbpedia.org/ontology/>
PREFIX c: <http://dbpedia.org/resource/Category:>
SELECT ?s ?author
WHERE {
?s rdf:type o:Book .
?s o:author ?author .
?author ?incategory c:American_atheists .
}

Get structure of RDF graph by SPARQL query

How can I get only triples which represent graph structure - class and properties hierarchy (i.e. without individuals, property values)?
It seems that I need rdf:type, owl:class and etc. triplets. So that is my variant:
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX owl: <http://www.w3.org/2002/07/owl#>
select ?s ?p ?o
where
{
{
graph <http://graph.org/gr>
{
?s rdf:type ?o.
?s ?p ?o.
}
FILTER
(?o IN (owl:Class, owl:DatatypeProperty, owl:AnnotationProperty, owl:ObjectProperty, owl:DataRange, owl:Ontology,
owl:DataRange,owl:DeprecatedClass,owl:DeprecatedProperty,owl:OntologyProperty,rdfs:Class,owl:Restriction,owl:InverseFunctionalProperty,
owl:FunctionalProperty,owl:AllDisjointClasses,rdf:Property, rdfs:Datatype )
)
}
UNION
{
graph <http://graph.org/gr>
{
?s ?p ?o.
}
FILTER
(?p IN (rdfs:subClassOf,rdfs:subPropertyOf,rdfs:domain,rdfs:range,rdfs:label,rdfs:comment,rdfs:member,
rdf:first,rdf:rest,owl:allValuesFrom,owl:someValuesFrom,owl:AnnotationProperty,owl:equivalentClass,
owl:equivalentProperty,owl:hasValue,owl:OntologyProperty,owl:SymmetricProperty,owl:TransitiveProperty,
owl:versionInfo,owl:priorVersion,owl:oneOf,owl:maxCardinality,owl:minCardinality,owl:inverseOf,
owl:incompatibleWith,owl:intersectionOf,owl:imports,owl:backwardCompatibleWith,owl:AllDifferent,
owl:differentFrom,owl:disjointWith,owl:distinctMembers,owl:complementOf,owl:cardinality,owl:unionOf,owl:onProperty))
}
}

SPARQL Query for list of ALL Classes related to Person

I want to make a SPARQL query which returns a list of all Ontology classes/properties which are related to Person. For eg., like the subclasses (derived from) of Person
<rdfs:subClassOf rdf:resource="http://dbpedia.org/ontology/Person"/>
or have a domain/range of Person
<rdfs:domain rdf:resource="http://dbpedia.org/ontology/Person"/>.
For example, the results like "http://dbpedia.org/ontology/OfficeHolder" & "http://dbpedia.org/ontology/Astronaut" should be returned by the query, as the first one has rdfs:domain Person while the second one was a rdfs:subClassOf Person.
Here's the query I've written:
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX owl: <http://www.w3.org/2002/07/owl#>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX dbo: <http://dbpedia.org/ontology/>
select distinct ?s
where {
{
?s rdfs:domain dbo:Person .
}
union
{
?s rdfs:range dbo:Person .
}
union
{
?s rdfs:subClassOf dbo:Person .
}
}
Now, this query returns a list of all the classes that explicitly mention Person in their Properties, but miss out classes like Singer, which is a subclass of MusicalArtist, which is in the domain of Person.
I want a query that lists out all such classes/properties, which are related to Person, directly or by "inheritance". Any suggestions?
It seems, you confuse classes with properties... Read carefully RDFS 1.1, it is short.
If you want to retrieve both classes and properties "related to" dbo:Person, use property paths:
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX owl: <http://www.w3.org/2002/07/owl#>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX dbo: <http://dbpedia.org/ontology/>
SELECT DISTINCT ?p ?s WHERE
{
{
?s (rdfs:subPropertyOf|owl:equivalentProperty|^owl:equivalentProperty)*/
rdfs:domain/
(rdfs:subClassOf|owl:equivalentClass|^owl:equivalentClass)*
dbo:Person .
BIND (rdfs:domain AS ?p)
}
UNION
{
?s (rdfs:subPropertyOf|owl:equivalentProperty|^owl:equivalentProperty)*/
rdfs:range/
(rdfs:subClassOf|owl:equivalentClass|^owl:equivalentClass)*
dbo:Person .
BIND (rdfs:range AS ?p)
}
UNION
{
?s (rdfs:subClassOf|owl:equivalentClass|^owl:equivalentClass)*
dbo:Person .
BIND (rdfs:subClassOf AS ?p)
}
# FILTER (STRSTARTS(STR(?s), "http://dbpedia.org/"))
}

How to query DBpedia SPARQL by resource uri?

I'm querying DBpedia types in SPARQL (http://dbpedia.org/sparql) by resource's label
PREFIX owl: <http://www.w3.org/2002/07/owl#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX foaf: <http://xmlns.com/foaf/0.1/>
PREFIX dc: <http://purl.org/dc/elements/1.1/>
PREFIX skos: <http://www.w3.org/2004/02/skos/core#>
PREFIX : <http://dbpedia.org/resource/>
PREFIX ru: <http://ru.dbpedia.org/resource/>
PREFIX dbpedia2: <http://dbpedia.org/property/>
PREFIX dbpedia: <http://dbpedia.org/>
PREFIX dbo: <http://dbpedia.org/ontology/>
SELECT ?type ?superType WHERE { {
?res rdfs:label "HarryPotter"#en.
} UNION {
?redir dbo:wikiPageRedirects ?res .
?redir rdfs:label "HarryPotter"#en .
}
?res rdf:type ?type .
OPTIONAL {
?type rdfs:subClassOf ?superType .
}
}
It works fine.
But what if I know the exact resource - http://dbpedia.org/page/Harry_Potter? I tried something like:
?res a :Harry_Potter.
But it does not work.
How to query DBpedia types and supertypes if I know the resource URI? I can't figure out which property or operator I should use (e.g., rdfs:Resource, a, etc., which do not work)
When you write
?res a :Harry_Potter.
It doesn't work, because this means "a resource, which is of type :Harry_Potter". It is equivalent to
?res rdf:type :Harry_Potter.
:Harry_Potter identifies a resource and not the type, thus it should be used in place of ?res.
Also I think you mean Harry_Potter_(character), because that is the actual identifier and not redirect.
You query would be as simple as
SELECT ?type ?superType WHERE
{
# give me ?type of the resource
<http://dbpedia.org/resource/Harry_Potter_(character)> rdf:type ?type .
# give me ?superTypes of ?type
OPTIONAL {
?type rdfs:subClassOf ?superType .
}
}
You can just put the URI as the subject in there WHERE conditions.
SELECT ?title, ?releaseDate
WHERE {
<http://dbpedia.org/resource/Super_Mario_Bros._3> dbp:title ?title .
<http://dbpedia.org/resource/Super_Mario_Bros._3> dbo:releaseDate ?releaseDate .
}

Sesame repository not being updated using INSERT despite no error

I am trying to update a Sesame repository with data from dbpedia. I have the following query:
PREFIX owl: <http://www.w3.org/2002/07/owl#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX foaf: <http://xmlns.com/foaf/0.1/>
PREFIX dc: <http://purl.org/dc/elements/1.1/>
PREFIX : <http://dbpedia.org/resource/>
PREFIX dbpedia2: <http://dbpedia.org/property/>
PREFIX dbpedia: <http://dbpedia.org/>
PREFIX skos: <http://www.w3.org/2004/02/skos/core#>
INSERT{?s ?p ?o}
WHERE {
SERVICE <http://dbpedia.org/sparql>{
{:Rotavirus_vaccine ?p ?o.
}
UNION
{
?s ?p :Rotavirus_vaccine.
}
}
}
This query doesn't show any error doesn't update the repository. On the other hand, splitting the UNION into two separate queries and then updating the repository one by one works. Why do the queries work in isolation but not in union? The code of an individual query is:
INSERT{:Rotavirus_vaccine ?p ?o}
WHERE {
SERVICE <http://dbpedia.org/sparql>{
{:Rotavirus_vaccine ?p ?o.
}
}
}
?s ?p ?o must all be defined in a row for the template be meaningful. Any time a variable is not bound, no update is done.
In one branch of the UNION, ?s ?p are defined and in the other ?p ?o. So all 3 are not defined in the same row.
Either add a BIND or a FILTER e.g for the first part:
{:Rotavirus_vaccine ?p ?o. BIND(:Rotavirus_vaccine AS ?s) }
{?s ?p ?o. FILTER(?s = :Rotavirus_vaccine }
or use this
INSERT{:Rotavirus_vaccine ?p ?o.
?s ?p :Rotavirus_vaccine.
}
because exactly one of those is defined for each case.
I've been able to execute a functional query by using BIND for both clauses of the UNION. The code is:
INSERT{?s ?p ?o}
WHERE
{
SERVICE <dbpedia.org/sparql>
{
{:Rotavirus_vaccine ?p ?o. BIND(:Rotavirus_vaccine AS ?s)}
UNION {?s ?p :Rotavirus_vaccine. BIND(:Rotavirus_vaccine AS ?o) }
}
}