SPARQL 查询具有相同属性的个人
SPARQL query for individuals with same properties
我想识别所有与其他个体具有相同属性的个体。想象一下,有不同的购物清单,上面有不同的物品,可以购买或租用(对象属性)。为了让事情变得更复杂,我还想为停车支付准确的金额并行驶一定的距离(数据属性)。同时,存在提供不同物品的不同商店。
作为一个懒惰的人,我想为每个列表确定提供列表中所有项目的商店。
我相信这是对这个 question 的概括,但我不知道如何做到这一点。
我创建了一些样本个体:
@prefix : <http://www.shopping.org/model#> .
@prefix owl: <http://www.w3.org/2002/07/owl#> .
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix xml: <http://www.w3.org/XML/1998/namespace> .
@prefix xsd: <http://www.w3.org/2001/XMLSchema#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@base <http://www.shopping.org/model> .
<http://www.shopping.org/model> rdf:type owl:Ontology .
# Object Properties
:buy rdf:type owl:ObjectProperty .
:rent rdf:type owl:ObjectProperty .
# Data properties
:distance rdf:type owl:DatatypeProperty .
:parking rdf:type owl:DatatypeProperty .
# Classes
:Product rdf:type owl:Class .
:ShoppingList rdf:type owl:Class .
:Store rdf:type owl:Class .
# Individuals
:Apples rdf:type owl:NamedIndividual ,
:Product .
:Cereal rdf:type owl:NamedIndividual ,
:Product .
:List1 rdf:type owl:NamedIndividual ,
:ShoppingList ;
:buy :Apples ,
:Milk ;
:distance "9.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:List2 rdf:type owl:NamedIndividual ,
:ShoppingList ;
:buy :Cereal ,
:Milk ;
:rent :TV ;
:distance "5.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:Milk rdf:type owl:NamedIndividual ,
:Product .
:Store1 rdf:type owl:NamedIndividual ,
:Store ;
:buy :Apples ,
:Cereal ,
:Milk ,
:TV ;
:distance "9.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:Store2 rdf:type owl:NamedIndividual ,
:Store ;
:buy :Cereal ,
:Milk ;
:rent :TV ;
:distance "5.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:TV rdf:type owl:NamedIndividual ,
:Product .
# General axioms
[ rdf:type owl:AllDisjointClasses ;
owl:members ( :Product
:ShoppingList
:Store
)
] .
并且还尝试了一些初步查询。这是我拥有的最好的:
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 xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX : <http://www.shopping.org/model#>
SELECT DISTINCT ?list ?store ?prop
WHERE {
?list a :ShoppingList .
?store a :Store .
?list ?prop [] .
FILTER NOT EXISTS {
?list ?prop ?value .
FILTER NOT EXISTS {
?store ?prop ?value .
}
}
}
ORDER BY ?list ?store
但是,此查询 returns 商店和列表的所有组合,因为每家商店收取 10.0f 的停车费。
我怎样才能只过滤那些满足所有列表要求的商店?
另一个假设是,可能存在除 buy 和 rent 之外的其他商业模式,以及其他标准,即数据属性,它们是兴趣也一样。这就是为什么我不想指定这些属性,而是想使用变量。
这个查询做了我想要做的:
PREFIXES [as above]
PREFIX : <http://www.shopping.org/model#>
SELECT DISTINCT ?list ?store
WHERE {
?list a :ShoppingList .
?store a :Store .
FILTER NOT EXISTS {
?compat a owl:DatatypeProperty
FILTER NOT EXISTS {
?list ?compat ?value .
?store ?compat ?value .
}
}
FILTER NOT EXISTS {
?subset a owl:ObjectProperty .
?list ?subset ?value .
FILTER NOT EXISTS {
?store ?subset ?value .
}
}
}
ORDER BY ?list ?store
我的错误实际上只是我在过滤器之外定义了 ?prop。这导致它们成为解决方案的一部分,即我无法通过过滤器删除整个商店。
如果您愿意具体说明事物需要共同的特定 属性,您可以这样做。我已经清理了你的数据,因为它实际上没有必要的前缀声明。 如果您希望人们能够使用您提供的内容,请包含完整的数据。我没有添加 correct 前缀,但足以让事情正常进行。
示例数据
@prefix : <urn:ex:> .
@prefix owl: <file:///home/taylorj/tmp/data.ttl> .
@prefix xsd: <file:///home/taylorj/tmp/data.ttl> .
:Store1 a owl:NamedIndividual , :Store ;
:buy :Apples , :Cereal , :Milk , :TV ;
:distance "9.0"^^owl:float ;
:parking "10.0"^^owl:float .
:List2 a owl:NamedIndividual , :ShoppingList ;
:buy :Cereal , :Milk ;
:distance "5.0"^^owl:float ;
:parking "10.0"^^owl:float ;
:rent :TV .
:List1 a owl:NamedIndividual , :ShoppingList ;
:buy :Apples , :Milk ;
:distance "9.0"^^owl:float ;
:parking "10.0"^^owl:float .
:Store2 a owl:NamedIndividual , :Store ;
:buy :Cereal , :Milk ;
:distance "5.0"^^owl:float ;
:parking "10.0"^^owl:float ;
:rent :TV .
具体解决方案
首先,我们可以解决特定情况,即我们需要一个人拥有另一个人的 属性 值的 子集 属性( buy), 以及其他属性的交叉值 (distance, parking).
查询
prefix : <urn:ex:>
select ?list ?store {
#-- For each list and store
?list a :ShoppingList .
?store a :Store .
#-- Check that they have the same distance and parking.
?distance ^:distance ?list, ?store .
?parking ^:parking ?list, ?store .
#-- Check that every item to buy (or rent) on the list is also
#-- in the store to buy (or rent).
filter not exists {
values ?get { :buy :rent }
?list ?get ?item .
filter not exists {
?store ?get ?item
}
}
}
结果
--------------------
| list | store |
====================
| :List1 | :Store1 |
| :List2 | :Store2 |
--------------------
一般方法
通常,考虑消除不想要的结果会很有帮助。在这种情况下,您有两种属性:(i) 个体必须具有兼容值的属性,以及 (ii) 一个个体必须具有另一个个体的值的超集的属性。检查这些条件中的任何一个 不 是否成立并不难:
prefix : <urn:ex:>
select ?list ?store {
#-- For each list and store
?list a :ShoppingList .
?store a :Store .
#-- Check that for each "compatible property" ?compat,
#-- there must be some value that the ?list and the
#-- ?store have in common.
filter not exists {
values ?compat { :distance :parking }
filter not exists {
?list ?compat ?value .
?store ?compat ?value .
}
}
#-- Check that for each "subset property" ?subset,
#-- there is no value that the ?list contains that
#-- the store does not.
filter not exists {
values ?subset { :buy :rent }
?list ?subset ?value
filter not exists {
?store ?subset ?value
}
}
}
结果(相同)
--------------------
| list | store |
====================
| :List1 | :Store1 |
| :List2 | :Store2 |
--------------------
我想识别所有与其他个体具有相同属性的个体。想象一下,有不同的购物清单,上面有不同的物品,可以购买或租用(对象属性)。为了让事情变得更复杂,我还想为停车支付准确的金额并行驶一定的距离(数据属性)。同时,存在提供不同物品的不同商店。 作为一个懒惰的人,我想为每个列表确定提供列表中所有项目的商店。
我相信这是对这个 question 的概括,但我不知道如何做到这一点。
我创建了一些样本个体:
@prefix : <http://www.shopping.org/model#> .
@prefix owl: <http://www.w3.org/2002/07/owl#> .
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix xml: <http://www.w3.org/XML/1998/namespace> .
@prefix xsd: <http://www.w3.org/2001/XMLSchema#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@base <http://www.shopping.org/model> .
<http://www.shopping.org/model> rdf:type owl:Ontology .
# Object Properties
:buy rdf:type owl:ObjectProperty .
:rent rdf:type owl:ObjectProperty .
# Data properties
:distance rdf:type owl:DatatypeProperty .
:parking rdf:type owl:DatatypeProperty .
# Classes
:Product rdf:type owl:Class .
:ShoppingList rdf:type owl:Class .
:Store rdf:type owl:Class .
# Individuals
:Apples rdf:type owl:NamedIndividual ,
:Product .
:Cereal rdf:type owl:NamedIndividual ,
:Product .
:List1 rdf:type owl:NamedIndividual ,
:ShoppingList ;
:buy :Apples ,
:Milk ;
:distance "9.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:List2 rdf:type owl:NamedIndividual ,
:ShoppingList ;
:buy :Cereal ,
:Milk ;
:rent :TV ;
:distance "5.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:Milk rdf:type owl:NamedIndividual ,
:Product .
:Store1 rdf:type owl:NamedIndividual ,
:Store ;
:buy :Apples ,
:Cereal ,
:Milk ,
:TV ;
:distance "9.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:Store2 rdf:type owl:NamedIndividual ,
:Store ;
:buy :Cereal ,
:Milk ;
:rent :TV ;
:distance "5.0"^^xsd:float ;
:parking "10.0"^^xsd:float .
:TV rdf:type owl:NamedIndividual ,
:Product .
# General axioms
[ rdf:type owl:AllDisjointClasses ;
owl:members ( :Product
:ShoppingList
:Store
)
] .
并且还尝试了一些初步查询。这是我拥有的最好的:
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 xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX : <http://www.shopping.org/model#>
SELECT DISTINCT ?list ?store ?prop
WHERE {
?list a :ShoppingList .
?store a :Store .
?list ?prop [] .
FILTER NOT EXISTS {
?list ?prop ?value .
FILTER NOT EXISTS {
?store ?prop ?value .
}
}
}
ORDER BY ?list ?store
但是,此查询 returns 商店和列表的所有组合,因为每家商店收取 10.0f 的停车费。 我怎样才能只过滤那些满足所有列表要求的商店? 另一个假设是,可能存在除 buy 和 rent 之外的其他商业模式,以及其他标准,即数据属性,它们是兴趣也一样。这就是为什么我不想指定这些属性,而是想使用变量。
这个查询做了我想要做的:
PREFIXES [as above]
PREFIX : <http://www.shopping.org/model#>
SELECT DISTINCT ?list ?store
WHERE {
?list a :ShoppingList .
?store a :Store .
FILTER NOT EXISTS {
?compat a owl:DatatypeProperty
FILTER NOT EXISTS {
?list ?compat ?value .
?store ?compat ?value .
}
}
FILTER NOT EXISTS {
?subset a owl:ObjectProperty .
?list ?subset ?value .
FILTER NOT EXISTS {
?store ?subset ?value .
}
}
}
ORDER BY ?list ?store
我的错误实际上只是我在过滤器之外定义了 ?prop。这导致它们成为解决方案的一部分,即我无法通过过滤器删除整个商店。
如果您愿意具体说明事物需要共同的特定 属性,您可以这样做。我已经清理了你的数据,因为它实际上没有必要的前缀声明。 如果您希望人们能够使用您提供的内容,请包含完整的数据。我没有添加 correct 前缀,但足以让事情正常进行。
示例数据
@prefix : <urn:ex:> .
@prefix owl: <file:///home/taylorj/tmp/data.ttl> .
@prefix xsd: <file:///home/taylorj/tmp/data.ttl> .
:Store1 a owl:NamedIndividual , :Store ;
:buy :Apples , :Cereal , :Milk , :TV ;
:distance "9.0"^^owl:float ;
:parking "10.0"^^owl:float .
:List2 a owl:NamedIndividual , :ShoppingList ;
:buy :Cereal , :Milk ;
:distance "5.0"^^owl:float ;
:parking "10.0"^^owl:float ;
:rent :TV .
:List1 a owl:NamedIndividual , :ShoppingList ;
:buy :Apples , :Milk ;
:distance "9.0"^^owl:float ;
:parking "10.0"^^owl:float .
:Store2 a owl:NamedIndividual , :Store ;
:buy :Cereal , :Milk ;
:distance "5.0"^^owl:float ;
:parking "10.0"^^owl:float ;
:rent :TV .
具体解决方案
首先,我们可以解决特定情况,即我们需要一个人拥有另一个人的 属性 值的 子集 属性( buy), 以及其他属性的交叉值 (distance, parking).
查询
prefix : <urn:ex:>
select ?list ?store {
#-- For each list and store
?list a :ShoppingList .
?store a :Store .
#-- Check that they have the same distance and parking.
?distance ^:distance ?list, ?store .
?parking ^:parking ?list, ?store .
#-- Check that every item to buy (or rent) on the list is also
#-- in the store to buy (or rent).
filter not exists {
values ?get { :buy :rent }
?list ?get ?item .
filter not exists {
?store ?get ?item
}
}
}
结果
--------------------
| list | store |
====================
| :List1 | :Store1 |
| :List2 | :Store2 |
--------------------
一般方法
通常,考虑消除不想要的结果会很有帮助。在这种情况下,您有两种属性:(i) 个体必须具有兼容值的属性,以及 (ii) 一个个体必须具有另一个个体的值的超集的属性。检查这些条件中的任何一个 不 是否成立并不难:
prefix : <urn:ex:>
select ?list ?store {
#-- For each list and store
?list a :ShoppingList .
?store a :Store .
#-- Check that for each "compatible property" ?compat,
#-- there must be some value that the ?list and the
#-- ?store have in common.
filter not exists {
values ?compat { :distance :parking }
filter not exists {
?list ?compat ?value .
?store ?compat ?value .
}
}
#-- Check that for each "subset property" ?subset,
#-- there is no value that the ?list contains that
#-- the store does not.
filter not exists {
values ?subset { :buy :rent }
?list ?subset ?value
filter not exists {
?store ?subset ?value
}
}
}
结果(相同)
--------------------
| list | store |
====================
| :List1 | :Store1 |
| :List2 | :Store2 |
--------------------