Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
286 views
in Technique[技术] by (71.8m points)

Sparql - How to constuct RDF by selecting MAX values of objects grouped by properties?

sorry for the irrevelant title, I'm French and I didn't know how to expose my problem. I think the best way to explain it is with an example.

I have some RDF sets like this one:

prefix p: <http://localhost/rdf/>

p:set p:hasTitle p:val1 .
p:set p:hasTitle p:val2 .
p:set p:hasAuthor p:val3 .
p:set p:hasAuthor p:val4 .

p:val1 p:hasValue "Harry Peter" .
p:val1 p:hasScore 0.30 .

p:val2 p:hasValue "Harry Potter" .
p:val2 p:hasScore 0.90 .

p:val3 p:hasValue "J. K. Rowling".
p:val3 p:hasScore 0.90 .

p:val4 p:hasValue "Joanne Rowling" .
p:val4 p:hasScore 0.50 .

I want to construct another graph with a sparql query, with only the values with the best score for each distinct property. In this example, the query is supposed to return this:

prefix p: <http://localhost/rdf/>

p:set p:hasTitle p:val2 .
p:set p:hasAuthor p:val3 .

p:val2 p:hasValue "Harry Potter" .
p:val2 p:hasScore 0.90 .

p:val3 p:hasValue "J. K. Rowling" .
p:val3 p:hasScore 0.90 .

For now I have tried something like this:

PREFIX p:    <http://localhost/rdf/>

CONSTRUCT {
    p:root p:hasSameAsSet ?saSet .
    ?saSet ?prop ?bestVal .
    ?bestVal ?p ?v
} 

WHERE { 
    ?s p:hasSameAsSet ?saSet .
    ?saSet ?prop ?val .
    ?bestVal ?p ?v .
    ?bestVal p:hasQualityScore ?m
    {
        SELECT (MAX(?score) AS ?m)
        WHERE { 
            ?val p:hasQualityScore ?score 
        } GROUP BY ?prop
    }    
}

I'm discovering Sparql and I know I'm missing important things. I hope someone can help me, thank you very much ! If my question isn't clear, I can try to explain it better. Don't worry for your answers, I'm better at reading than writing ;)

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

AKSW's comment is spot on. Your query is very close as is, but the subquery is executed first, so it needs enough information get the grouping right, and you also need to project the variables from within it that will let you do the join with the outer query results.

E.g., a query like this gets you the maximal value for each property:

  select ?prop (max(?val_) as ?val) {
    ?sub ?prop ?val_
  }
  group by ?prop

Then you just need to nest that within an outer query that finds, for each property and max value, the subject that had it:

select ?sub ?prop ?val {
    ?sub ?prop ?val
    { select ?prop (max(?val_) as ?val) {
        ?sub ?prop ?val_
      }
      group by ?prop
    }
}

(Note that there could be multiple values of ?sub that have the maximal value.) Adding any extra information that you need to the outer query and then turning it into a constuct query shouldn't be hard, given what you've already got in your existing query.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...