如何在任意长度的sparql路径中使用Union/or?

how to use Union/or in sparql path with arbitrary length?

我正在使用以下查询从 DBPedia ontology 中查找具有城市域(或城市超类)或国家范围(或国家超类)的所有属性。当我使用固定长度的路径时没有问题但是当我用 * 定义任意长度的路径时,我得到这个错误:

Virtuoso 37000 Error SP031: SPARQL compiler: Variable '_::trans_subj_6_4' is used in subexpressions of the query but not assigned

我的 SPARQL:

define sql:signal-void-variables 1
define input:default-graph-uri <http://dbpedia.org>

PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX dbo: <http://dbpedia.org/ontology/>
PREFIX res: <http://dbpedia.org/resource/>
PREFIX owl:<http://www.w3.org/2002/07/owl#>
PREFIX rdfs:<http://www.w3.org/2000/01/rdf-schema#>

select ?property where{
  { ?property rdfs:domain/^rdfs:subClassOf* dbo:City }
  UNION
  { ?property rdfs:range/^rdfs:subClassOf* dbo:Country } 
}

此外,当我输入任何数字而不是 * 时,我也会遇到同样的错误。我正在使用 Virtuoso 作为 DBPedia SPARQL 端点。

使用 VALUES 而不是 UNION(如果可以)

Virtuoso 给你的错误更多是关于 属性 路径和 union 的实现,而不是实际的 SPARQL 查询。查询的 SPARQL 部分看起来是正确的。 (我不能说 Virtuoso 具体的 定义。)

在原始 SPARQL 标准中许多需要 union 的地方,您现在可以使用 values 来指定变量可以使用的特定值有。它通常会导致更具可读性的查询(至少在我看来是这样),并且某些端点(例如 Virtuoso)似乎可以更好地处理它。

使用 values(并使用端点的 Web 界面使用的 dbpedia-owl 前缀),您query变成如下,Virtuosoreturns你要找的是:

select ?property where {
  values (?p ?v) { (rdfs:domain dbpedia-owl:City)
                   (rdfs:range dbpedia-owl:Country) }
  ?property ?p ?class  .
  ?class ^rdfs:subClassOf* ?v .
}

SPARQL results

其他注意事项

Also when I put any number instead of *, I get same error. I'm using Virtuoso as DBPedia SPARQL endpoint.

虽然 Virtuoso 接受 属性 路径长度的 {n,m} 符号,但请注意,虽然这些出现在 属性 路径的某些草稿中,但它们实际上并没有实现进入 SPARQL 1.1 标准。 Virtuoso 仍然接受它们,但如果您使用它们,您可能无法将您的查询用于其他端点。