我将相册的歌曲建模如下:
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@prefix xsd: <http://www.w3.org/2001/XMLSchema#> .
@prefix md: <http://example.com/music-discography#> .
md:album1 md:songs-of-album md:song1 .
md:album1 md:songs-of-album md:song2 .
md:album1 md:songs-of-album md:song3 .
md:song1 md:name "Song 1" .
md:song2 md:name "Song 2" .
md:song3 md:name "Song 3" .
md:song1 md:position "1"^^xsd:integer .
md:song2 md:position "2"^^xsd:integer .
md:song3 md:position "3"^^xsd:integer .
我希望能够访问专辑中最后一首歌的名称。
因此,我想通过计算一张专辑中包含的歌曲数量,首先获得最后一首歌的md:position
SELECT (COUNT(*) AS ?lastposition)
WHERE {
{ md:album1 md:songs-of-album ?songInnerQuery }
}
产生正确的结果&#34; 3&#34;:
<results>
<result>
<binding name="lastposition">
<literal datatype="http://www.w3.org/2001/XMLSchema#integer">3</literal>
</binding>
</result>
</results>
然后我想通过使用上面的查询作为子查询来重用此结果。我怎样才能做到这一点?我尝试了以下方法:
SELECT ?songName WHERE {
?song md:position ?lastposition .
?song md:name ?songName
{ SELECT (COUNT(*) AS ?lastposition)
WHERE {
{ md:album1 md:songs-of-album ?songInnerQuery }
}
}
}
然而,这不起作用并产生所有三首歌曲:
<results>
<result>
<binding name="songName"><literal>Song 3</literal></binding>
</result>
<result>
<binding name="songName"><literal>Song 2</literal></binding>
</result>
<result>
<binding name="songName"><literal>Song 1</literal></binding>
</result>
</results>
为什么会发生这种情况?这样做的正确方法是什么?我正在使用triplestore 4store。
答案 0 :(得分:1)
看起来它是4store中的一个错误。您应该向他们报告。你在Jena得到的结果是你所期望的:
<?xml version="1.0"?>
<sparql xmlns="http://www.w3.org/2005/sparql-results#">
<head>
<variable name="songName"/>
</head>
<results>
<result>
<binding name="songName">
<literal>Song 3</literal>
</binding>
</result>
</results>
</sparql>
但是,您不需要子查询来执行此操作。你可以把歌曲放在一个位置,使得没有更多位置的歌曲:
SELECT ?songName WHERE {
?song md:position ?lastposition .
?song md:name ?songName
filter not exists {
?song_ md:position ?position
filter (?position > ?lastposition)
}
}