I am trying to figure out how Jena TDB handles SPARQL queries with multiple FROM clauses on the physical query plan level.
I would like to know how Jena TDB handles executing a query over different graphs.
I have made some small experiments and looked at the query algebra, however, it is not clear to me how the FROM clauses affect the algebra.
It looks like that the FROM clauses are discarded in the algebra. I expect that the algebra is evaluated over the union of the graphs, but I would like to be sure.
I have the following quads:
<http://example.com/book2/> <http://example.com/price> "5"^^<http://www.w3.org/2001/XMLSchema#integer> <http://example.com/A> .
<http://example.com/book2/> <http://example.com/title> "Lord of the Rings" <http://example.com/B> .
and the following query:
SELECT (AVG(?price) as ?total)
FROM <http://example.com/A>
FROM <http://example.com/B>
WHERE {
?book <http://example.com/price> ?price .
?book <http://example.com/title> ?title .
}
./tdbquery --loc test --query test.sparql --explain
The query algebra looks as follows:
INFO exec :: ALGEBRA
(project (?total)
(extend ((?total ?.0))
(group () ((?.0 (avg ?price)))
(bgp (triple ?book <http://example.com/price> ?price)))))
When I execute the query over the data I receive the expected result.
FROM (and FROM NAMED) aren't really part of the query, but indications of what the dataset to be queried ought to be. These clauses don't alter what the query will do, only what it operates on, so you don't see them in the algebra.
What a particular processor does with that information varies:
some processors will build the requested dataset (even downloading data)
but it is also common to provide a dataset explicitly in APIs (e.g. query(query_string, dataset)) in which case the processor will ignore it since a dataset has been provided.
a dataset might also be supplied with in a SPARQL protocol request, in which case, as with the API call, the processor will ignore the NAMED clause.
Now a TDB database is a dataset, but TDB has a special feature called 'dynamic datasets' which used FROM and FROM NAMED to form a sub-dataset in effect, limiting the graphs queried to those mentioned in the FROM clauses.
Related
When using SPARQL to query RDF dataset, the same query can be written in many different ways. For example, sparql queries are always permutation-invariant with respect to some clauses inside it. Also, we can rename the variables inside a sparql query. But how can we identify those identical SPARQL queries? Ideally, there should be a python package that can parse a sparql query (i.e., a string object) into a query object, and different strings share the same underlying query are parsed into the same object, then we can simply compare the parsed query objects to determine whether two sparql queries are identical. Is there any tool like this (seems prepareQuery() in rdflib doesn't work in this way)? If not, then what should I do?
Semantically identical queries example:
SELECT ?x WHERE { ?x foaf:haha ?k .\n ?person foaf:knows ?x .}
SELECT ?s WHERE { ?person foaf:knows ?s .\n ?s foaf:haha ?k .}
The paper "Generating SPARQL Query Containment Benchmarks
using the SQCFramework" by Muhammad Seleem et al., mentions "SPARQL query containment solvers" where
Query containment is the problem of deciding if the result set of a query Q1 is included
in the result set of another query Q2
If you use such a solver to test whether the result set of Q1 is a subset of Q2 and vice versa, you have established that they are semantically identical.
As for your "off-the-shelf tool": the former paper mentions that those are tested in another paper "Evaluating and benchmarking sparql query containment solvers." by M.W. Chekol et al..
As for the complexity and computability, the latter paper mentions:
The query containment problem for full SPARQL is undecidable [15, 1].
Hence, it is necessary to reduce SPARQL in order to consider it. A
double exponential upper bound has been proven for the containment and
equivalence problems of SPARQL queries without OPTIONAL , FILTER and
under set semantics [7].
However, query containment in both directions is only one way to determine identity of queries. I am unaware whether there is a proof of a better complexity/computability for query identity than for query containment (or a proof on the contrary).
We're running SPARQL queries on some clinical ontology data in our MarkLogic server. Our queries look like the following:
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX cts: <http://marklogic.com/cts#>
SELECT *
FROM <http://example/ontologies/snomedct>
WHERE {
?s rdfs:label ?o .
FILTER cts:contains(?o, cts:word-query("Smoke*", "wildcarded"))
}
LIMIT 10
We expected to get sorted results based off of relevance score, but instead they seemed to be in some random order. Tried many ways with the query but nothing worked. After some research we found this statement in the MarkLogic docs:
When understanding the order an expression returns in, there are two
main rules to consider:
cts:search expressions always return in relevance order (the most relevant to the least relevant).
XPath expressions always return in document order.
Does this mean that cts:contains is a XPath expression that always return in document order? If that's the case, how can we construct a SPARQL query that returns in relevance order?
Thanks,
Kevin
In the example you have, the language you are using is SPARQL - with a fragment filter of the cts:contains.
IN this case, the cts:contains is only useful in isolating fragment IDs that match - thus filtering the candidate documents used in the SPARQL query. Therefore, I do not believe that the the cts relevance is taken into account.
However, you could possibly get results you are looking for in a different way: Do an actual cts:search on the documents in question - then filter them using a cts:triple-range-query.
https://docs.marklogic.com/cts:triple-range-query
I want to write a SPARQL query that cross references an entity with a single time point with a set of entities that have time ranges. Here's the graph pattern:
{
?entity :atTime ?probe.
?interval :startTime ?start ;
:endTime ?end .
FILTER (?start < ?probe)
FILTER (?probe < ?end)
}
One way for the query engine to run this is to find all the entities with :atTime defined, find all of the intervals, and perform all of these checks. But MarkLogic (and most databases) have facilities for range indices, so that this can be done much more efficiently.
I have seen in the ML docs that you can use cts:contains in SPARQL to reach its string indices. Is there a way to do something similar with range queries?
Some databases recognize design patterns in code like what I have quoted here, and they do that optimization themselves (which keeps the code standard!). Perhaps MarkLogic does this? I can't find any documentation telling me about this.
MarkLogic's triple index can perform range queries directly, so there's no need for a separate range index. The optimizer should recognize and optimize this query pattern.
I have stored large amount of RDF data into a relational database with the help of rdflib_sqlalchemy.SQLAlchemy.Now I want to execute Sparql query over the same.I can not find any thing to know how to implement sparql query here.
Can anyone help.
Including sample code would make it easier to know what you are after but see the documentation on querying an RDFLib graph with SPARQL.
Using the example from the rdflib-sqlalchemy README where graph is the name of the open graph.
rq = "select ?s where {?s ?p ?o} limit 10"
results = graph.query(rq)
for row in results:
print row.s
I tried one SPARQL query in two different engines:
Protege 4.3 - SPARQL query tab
Jena 2.11.0
While the query is the same the results returned by these two tools are different.
I tried a DESCRIBE query like the following:
DESCRIBE ?x
WHERE { ?x :someproperty "somevalue"}
Results from protege give me tuples that take ?x as subject/object; while the ones from jena are that take ?x as subject only.
My questions are:
Is the syntax of SPARQL uniform?
If I want DESCRIBE to work as in protege, what should I do in Jena?
To answer your first question yes the SPARQL syntax is uniform since you've used the same query in both tools. However what I think you are actually asking is should the results for the two tools be different or not? i.e. are the semantics of SPARQL uniform
In the case of DESCRIBE then yes the results are explicitly allowed to be different by the SPARQL specification i.e. no the semantics of SPARQL are not uniform but this is only in the case of DESCRIBE.
See Section 16.4 DESCRIBE (Informative) of the SPARQL Specification which states the following:
The query pattern is used to create a result set. The DESCRIBE form
takes each of the resources identified in a solution, together with
any resources directly named by IRI, and assembles a single RDF graph
by taking a "description" which can come from any information
available including the target RDF Dataset. The description is
determined by the query service
The important part of this is the last couple of sentences that say the description is determined by the query service. This means that both Protege's and Jena's answers are correct since they are allowed to choose how they form the description.
Changing Jena DESCRIBE handling
To answer the second part of your question you can change how Jena processes DESCRIBE queries by implementing a custom DescribeHandler and an associated DescribeHandlerFactory. You then need to register your factory like so:
DescribeHandlerRegistry.get().set(new YourDescribeHandlerFactory());