kdb*_*man 4 rdf semantic-web sparql dbpedia linked-data
使用 SPARQL 1.1 的value,以下查询返回以Einstein或Knuth作为主语的所有谓词(及其标签)。
PREFIX dbp: <http://dbpedia.org/resource/>
SELECT DISTINCT ?sub ?outpred ?label
{
VALUES ?sub { dbp:Albert_Einstein dbp:Donald_Knuth }
?sub ?outpred [] .
?outpred <http://www.w3.org/2000/01/rdf-schema#label> ?label .
}
Run Code Online (Sandbox Code Playgroud)
是否可以使用此值功能来公开谓词的交集而不是并集?或者我误解了价值观的用途?
举一个简化的例子,假设有以下三元组:
<Einstein> <influenced> <John>
<Einstein> <influenced> <Knuth>
<Einstein> <born> <Mars>
<Einstein> <died> <Los Angeles>
<Knuth> <influenced> <Kirby>
<Knuth> <born> <Mars>
<Knuth> <wrote> <TAOCP>
<Knuth> <drove> <Truck>
Run Code Online (Sandbox Code Playgroud)
我得到的“联合”是附加到任一主题的所有唯一谓词(为了清楚起见,以行分隔):
| ?sub | ?pred |
-------------------------
<Einstein> <influenced>
<Knuth> <influenced>
<Einstein> <born>
<Knuth> <born>
<Einstein> <died>
<Knuth> <wrote>
<Knuth> <drove>
Run Code Online (Sandbox Code Playgroud)
我所追求的“交叉点”是两个主题共有的所有独特谓词:
| ?sub | ?pred |
-------------------------
<Einstein> <influenced>
<Knuth> <influenced>
<Einstein> <born>
<Knuth> <born>
Run Code Online (Sandbox Code Playgroud)
您可以使用这样的查询。诀窍是按谓词分组,并且只采用那些恰好有两个主语(爱因斯坦和高德纳)的谓词。
\n\nselect distinct ?outpred ?label\n{\n values ?sub { dbp:Albert_Einstein dbp:Donald_Knuth }\n ?sub ?outpred [] .\n ?outpred <http://www.w3.org/2000/01/rdf-schema#label> ?label .\n}\ngroup by ?outpred ?label\nhaving count(distinct ?sub) = 2\nRun Code Online (Sandbox Code Playgroud)\n\n当然,这确实需要检索联合所需的所有数据,然后将其压缩。我不认为这会成为一个大问题,但如果是这样(例如,如果您尝试对许多主题进行交集),那么您也可以单独列出主题:
\n\nselect distinct ?outpred ?label\n{\n dbp:Albert_Einstein ?outpred [].\n dbp:Donald_Knuth ?outpred [].\n ?outpred <http://www.w3.org/2000/01/rdf-schema#label> ?label .\n}\nRun Code Online (Sandbox Code Playgroud)\n\n\n\n\n是否可以使用此 VALUES 功能来公开交集而不是谓词的并集?或者我误解了\n VALUES 的用途?
\n
值本质上是与其他绑定连接的另一组绑定,因此它无法按照您想要的方式为您进行交集。然而,要做一个你在这里寻找的那种“交叉点”并不太难:
\n\nselect distinct ?outpred ?label\n{\n dbp:Albert_Einstein ?outpred [] .\n dbp:Donald_Knuth ?outpred [] .\n ?outpred <http://www.w3.org/2000/01/rdf-schema#label> ?label .\n}\nRun Code Online (Sandbox Code Playgroud)\n\n现在,这可能需要编写很多三元组模式,因此您可能需要一些查询,其中唯一需要更改的是值列表。您可以指定值,然后按属性和标签(即非值变量)进行分组,然后仅采用count(distinct ?sub)您指定的值数量的解决方案。例如:
select distinct ?outpred ?label\n{\n values ?sub { dbp:Albert_Einstein dbp:Donald_Knuth }\n ?sub ?outpred [] .\n ?outpred <http://www.w3.org/2000/01/rdf-schema#label> ?label .\n}\ngroup by ?outpre ?label\nhaving count(distinct ?sub) = 2\nRun Code Online (Sandbox Code Playgroud)\n\n这样,为了达到count(distinct ?sub)2,您必须同时?sub ?outpred []匹配和。 ?sub = Einstein?sub = Knuth
我们可以使用 DBpedia 端点来解决这些问题。首先,一个简化的查询:
\n\nselect distinct ?s ?p where {\n values ?s { dbpedia:Albert_Einstein dbpedia:Donald_Knuth }\n ?s ?p []\n}\nRun Code Online (Sandbox Code Playgroud)\n\n\n\ns p\nhttp://dbpedia.org/resource/Albert_Einstein http://www.w3.org/1999/02/22-rdf-syntax-ns#type\nhttp://dbpedia.org/resource/Donald_Knuth http://www.w3.org/1999/02/22-rdf-syntax-ns#type\nhttp://dbpedia.org/resource/Albert_Einstein http://www.w3.org/2002/07/owl#sameAs\nhttp://dbpedia.org/resource/Donald_Knuth http://www.w3.org/2002/07/owl#sameAs\n\xe2\x8b\xae \xe2\x8b\xae\nRun Code Online (Sandbox Code Playgroud)\n\n现在,当我们仍在选择?s时要求交集是没有意义的,因为 Einstein ≠ Knuth,所以永远不会有任何交集。但我们可以在?p上取交集。这是一个获取所有具有值的属性的查询:
\n\nselect distinct ?p where {\n dbpedia:Albert_Einstein ?p [] .\n dbpedia:Donald_Knuth ?p []\n}\nRun Code Online (Sandbox Code Playgroud)\n\n\n\n类似的查询为我们计算结果:
\n\nselect (count(distinct ?p) as ?np) where {\n dbpedia:Albert_Einstein ?p [] .\n dbpedia:Donald_Knuth ?p [] .\n}\nRun Code Online (Sandbox Code Playgroud)\n\n他们都拥有 45 个属性。
\n\n按查询分组是
\n\nselect distinct ?p where {\n values ?s { dbpedia:Albert_Einstein dbpedia:Donald_Knuth }\n ?s ?p []\n}\ngroup by ?p\nhaving count(?s) = 2\nRun Code Online (Sandbox Code Playgroud)\n\n现在让我们确保其他方法得到相同的结果:
\n\nselect (count(*) as ?np) where {\n select distinct ?p where {\n values ?s { dbpedia:Albert_Einstein dbpedia:Donald_Knuth }\n ?s ?p []\n }\n group by ?p\n having count(distinct ?s) >= 2\n}\nRun Code Online (Sandbox Code Playgroud)\n\n这也返回 45,所以我们看到我们得到了相同的结果。
\n