介绍
RDF is a directed, labeled graph data format for representing information in the Web. RDF is often used to represent, among other things, personal information, social networks, metadata about digital artifacts, as well as to provide a means of integration over disparate sources of information. This specification defines the syntax and semantics of the SPARQL query language for RDF. The SPARQL query language for RDF is designed to meet the use cases and requirements identified by the RDF Data Access Working Group in RDF Data Access Use Cases and Requirements [UCNR].
SPARQL即SPARQL Protocol and RDF Query Language的递归缩写,被专门设计用来访问和操作RDF数据,是语义网的核心技术之一。W3C的RDF数据存取小组(RDF Data Access Working Group, RDAWG)对其进行了标准化。2008年1月15日,SPARQL正式成为一项W3C推荐标准。
我们可以将抽取的RDF三元组导入Apache Jena Fuseki,通过SPARQL进行查询:
简单查询
SQL | sparql |
---|---|
SELECT title from book where id='book1' | SELECT ?title WHERE { <http://example.org/book/book1> <http://purl.org/dc/elements/1.1/title> ?title . } |
Query Result:
title |
---|
"SPARQL Tutorial" |
多字段匹配
RDF 数据
代码语言:javascript复制@prefix foaf: <http://xmlns.com/foaf/0.1/> .
_:a foaf:name "Johnny Lee Outlaw" .
_:a foaf:mbox <mailto:jlow@example.com> .
_:b foaf:name "Peter Goodguy" .
_:b foaf:mbox <mailto:peter@example.org> .
_:c foaf:mbox <mailto:carol@example.org> .
sparql:
代码语言:javascript复制PREFIX foaf: <http://xmlns.com/foaf/0.1/>
SELECT ?name ?mbox
WHERE
{ ?x foaf:name ?name .
?x foaf:mbox ?mbox }
SQL:
代码语言:javascript复制SELECT ?name ?mbox
from foaf
查询结果:
name | mbox |
---|---|
"Johnny Lee Outlaw" | mailto:jlow@example.com |
"Peter Goodguy" | mailto:peter@example.org |
数据属性匹配
对于string类型,需要用双引号包裹起来。
sparql:
代码语言:javascript复制SELECT ?v WHERE { ?v ?p "cat" }
SQL:
代码语言:javascript复制SELECT *
from ns
where p='cat'
对于数字类型:
sparql:
代码语言:javascript复制SELECT ?v WHERE { ?v ?p 42 }
SQL:
代码语言:javascript复制SELECT * from ns where p= 42
另外,在spaql里可以指定匹配的类型:
代码语言:javascript复制SELECT ?v WHERE { ?v ?p "abc"^^<http://example.org/datatype#specialDatatype> }
条件过滤
模糊匹配
通过regex
函数可以进行字符串正则匹配,通过FILTER
进行过滤
PREFIX dc: <http://purl.org/dc/elements/1.1/>
SELECT ?title
WHERE { ?x dc:title ?title
FILTER regex(?title, "web", "i" )
}
SQL:
代码语言:javascript复制SELECT * from table where title like '%web%'
数字比较
代码语言:javascript复制PREFIX dc: <http://purl.org/dc/elements/1.1/>
PREFIX ns: <http://example.org/ns#>
SELECT ?title ?price
WHERE { ?x ns:price ?price .
FILTER (?price < 30.5)
?x dc:title ?title . }
SQL:
代码语言:javascript复制SELECT title,price from table where price <30.5
OPTIONAL(可选值)
RDF 数据,用户Bob没有mbox,而用户Alice有两个mbox
代码语言:javascript复制@prefix foaf: <http://xmlns.com/foaf/0.1/> .
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
_:a rdf:type foaf:Person .
_:a foaf:name "Alice" .
_:a foaf:mbox <mailto:alice@example.com> .
_:a foaf:mbox <mailto:alice@work.example> .
_:b rdf:type foaf:Person .
_:b foaf:name "Bob" .
正常查询,因为Bob没有mbox,所以查询不出来,可以通过OPTIONAL
标记mbox为可选,这样Bob就可以查询出来。
sparql:
代码语言:javascript复制PREFIX foaf: <http://xmlns.com/foaf/0.1/>
SELECT ?name ?mbox
WHERE { ?x foaf:name ?name .
OPTIONAL { ?x foaf:mbox ?mbox }
}
查询结果
name | mbox |
---|---|
"Alice" | mailto:alice@example.com |
"Alice" | mailto:alice@work.example |
"Bob" |
可以看到, "Bob"
的 mbox
是空值。
对于关系型数据库,可以假设两个表
User { id,name} Mbox {id,uid,name} (uid为外键)
对应的sql:
代码语言:javascript复制SELECT user.name AS name,mbox.name AS mboxName
FROM User user
LEFT OUTER JOIN Mbox mbox ON mbox.uid=user.id
OPTIONAL FILTER
OPTIONAL 可以和FILTER 组合使用
代码语言:javascript复制PREFIX dc: <http://purl.org/dc/elements/1.1/>
PREFIX ns: <http://example.org/ns#>
SELECT ?title ?price
WHERE { ?x dc:title ?title .
OPTIONAL { ?x ns:price ?price . FILTER (?price < 30) }
}
UNION
Data:
代码语言:javascript复制@prefix dc10: <http://purl.org/dc/elements/1.0/> .
@prefix dc11: <http://purl.org/dc/elements/1.1/> .
_:a dc10:title "SPARQL Query Language Tutorial" .
_:a dc10:creator "Alice" .
_:b dc11:title "SPARQL Protocol Tutorial" .
_:b dc11:creator "Bob" .
_:c dc10:title "SPARQL" .
_:c dc11:title "SPARQL (updated)"
查询:
代码语言:javascript复制PREFIX dc10: <http://purl.org/dc/elements/1.0/>
PREFIX dc11: <http://purl.org/dc/elements/1.1/>
SELECT ?title
WHERE { { ?book dc10:title ?title } UNION { ?book dc11:title ?title } }
Query result:
代码语言:javascript复制title
"SPARQL Protocol Tutorial"
"SPARQL"
"SPARQL (updated)"
"SPARQL Query Language Tutorial"
排序
和sql一样,使用ORDER BY 排序,示例如下:
代码语言:javascript复制PREFIX foaf: <http://xmlns.com/foaf/0.1/>
SELECT ?name
WHERE { ?x foaf:name ?name ; :empId ?emp }
ORDER BY ?name DESC(?emp)
去重
和sql一样,使用DISTINCT来去重,示例如下:
代码语言:javascript复制PREFIX foaf: <http://xmlns.com/foaf/0.1/>
SELECT DISTINCT ?name WHERE { ?x foaf:name ?name }
判断是否存在
使用ask来判断是否有解决方案
代码语言:javascript复制PREFIX foaf: <http://xmlns.com/foaf/0.1/>
ASK { ?x foaf:name "Alice" ;
foaf:mbox <mailto:alice@work.example>