zoukankan      html  css  js  c++  java
  • Jena搭建SPARQL查询RDF数据

    1 Jena搭建SPARQL查询RDF数据

    1.1 Jena概要

    · SPARQL是W3C的RDF数据工作组设计的一种查询语言和协议,用于RDF数据的查询。经过类似于JDK安装时候的配置,可以在命令行运行SPARQL查询,也可以在安装了Jena API之后,在Java程序用使用SPARQL查询。

    1.2 Jena环境搭建

    · 到oracle官网上下载最新版本的JDK然后安装,地址:http://www.oracle.com/technetwork/java/javase/downloads/index.html

    · 可以从http://jena.sourceforge.net免费获得Jena的最新版本,或者直接从本站下载:jena-2.6.4.zip。

    · 将下载好的jena解压到摸个目录,如C:softdevelopjena

    · 添加环境变量,鼠标右键单击【我的电脑】-【属性】-【高级】-【环境变量】

    ■ 添加JDK系统变量PATH -> 值C:Program Files (x86)Javajdk1.7.0_21in

    ■ 添加Jena系统变量PATH -> 值C:softdevelopjenaat

    ■ 添加Jena根目录JENAROOT ->C:softdevelopjena

    · 如何上面没执行错误的话,在命令行执行sparql会返回

    No query string or query file

    如果执行sparql –h(或者sparql –help)就会返回命令sparql的帮助信息。

    1.3 执行一个简单的查询

    · SPARQL查询语句的执行格式是:

    sparql --data=<file> --query=<query>

    file是要查询的数据源,RDF文件或者RDF图文件;

    query是查询语句文件,以.rq为文件后缀。

    · 数据源,一个RDF文件r1.rdf,文档描述一些简单的人名信息,下面是类似三元组形式的数据表示。

    <?xml version="1.0"?>

    <rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"

      xmlns:vCard="http://www.w3.org/2001/vcard-rdf/3.0#">

      <rdf:Description rdf:about="http://somewhere/MattJones/">

        <vCard:FN>Matt Jones</vCard:FN>

          <vCard:N rdf:parseType="Resource">

            <vCard:Family>Jones</vCard:Family>

            <vCard:Given>Matthew</vCard:Given>

          </vCard:N>

      </rdf:Description>

      <rdf:Description rdf:about="http://somewhere/RebeccaSmith/">

        <vCard:FN>Becky Smith</vCard:FN>

        <vCard:N rdf:parseType="Resource">

          <vCard:Family>Smith</vCard:Family>

          <vCard:Given>Rebecca</vCard:Given>

        </vCard:N>

      </rdf:Description>

      <rdf:Description rdf:about="http://somewhere/JohnSmith/">

        <vCard:FN>John Smith</vCard:FN>

        <vCard:N rdf:parseType="Resource">

          <vCard:Family>Smith</vCard:Family>

          <vCard:Given>Jones</vCard:Given>

        </vCard:N>

      </rdf:Description>

      <rdf:Description rdf:about="http://somewhere/SarahJones/">

        <vCard:FN>Sarah Jones</vCard:FN>

        <vCard:N rdf:parseType="Resource">

          <vCard:Family>Jones</vCard:Family>

          <vCard:Given>Sarah</vCard:Given>

        </vCard:N>

      </rdf:Description>

    </rdf:RDF>

    · 查询语句q1.rq

    SELECT ?x

    WHERE { ?x  <http://www.w3.org/2001/vcard-rdf/3.0#FN>  "John Smith" }

    · 使用上面的查询语句查询r1.rdf文件中的数据的命令行语句就是

    sparql --data=r1.rdf --query=q1.rq 

    返回结果是:

    ---------------------------------

    | x                             |

    =================================

    | <http://somewhere/JohnSmith/> |

    ---------------------------------

    · 在执行上面的查询时,要保证数据文件和查询文件在当前目录下,否则命令中应该包括完整路径,即:

    sparql --data=c:sparql 1.rdf --query=c:sparqlq1.rq 

    2 对查询语句和查询结果的理解

    · 查询语句包括查询信息的名称以及名称应该符合的条件。条件子句以三元组形式出现,按照<主语,谓语,宾语>的顺序排列。查询条件也成为一个模式(Pattern)。查询的结果实际就是条件三元组与数据文件(或RDF图)中RDF三元组匹配的结果。

    · 语句中的 ? 加一个字母表示该字母是一个变量,比如 ?x,在SELECT后面的变量会显示在查询结果中,作为列名称出现。

    · 实际上,做到这一步之后,所有的事情只是修改模式,给模式添加一些条件了,非常简单。

    2.1 命名空间的简写替代

    · 如果查询所有具有名字的实例以及该实例的名字,那么查询语句如下

    SELECT ?x ?fname

    WHERE {?x  <http://www.w3.org/2001/vcard-rdf/3.0#FN>  ?fname}

    · 注意,“?x ?fname”之间是空格,不是逗号。如果有多个模式三元组,那么三元组之间用点号“.”隔开,比如

    SELECT ?givenName

    WHERE 

    { ?y  <http://www.w3.org/2001/vcard-rdf/3.0#Family>  "Smith" .

      ?y  <http://www.w3.org/2001/vcard-rdf/3.0#Given>  ?givenName .}

    · 这时候,模式中的谓词的URI都带一个长长的命名空间字符串,“http://www.w3.org/2001/vcard-rdf/3.0#”,

    能用一个简单的单词代替它应该会比较简单。实现简写URI的的语法是这样的:

    PREFIX vcard:<http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?givenName

    WHERE

    { ?y vcard:Family "Smith" .

      ?y vcard:Given  ?givenName .

    }

    · 语句PREFIX vcard:<http://www.w3.org/2001/vcard-rdf/3.0#> 定义了一个前缀单词vcard,在查询语句中,它与后面的命名空间等价。 

    2.2 过滤查询结果

    · 在查询语句中添加过滤条件的语句是

    FILTER regex(?x, "pattern" [, "flags"])

    FILTER是声明过滤,?x是过滤模式作用的变量,后面的pattern是具体的限制条件,比如

    PREFIX vcard: <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?g

    WHERE

    { ?y vcard:Given ?g .

    FILTER regex(?g, "r", "i") }

    这是要查询一些名字(Given Name),”r”表示,名字中必须出现的字母”r”或者”R”;”i”表示,对签名的字母限制,默认不加对大小写敏感,加上则对大小写不敏感。上面查询的结果是

    -------------

    | g         |

    =============

    | "Rebecca" |

    | "Sarah"   |

    -------------

     

    · 对数值限制的一个例子是:请查询r2.rdf文件

    PREFIX info <http://somewhere/peopleInfo#>

    SELECT ?resource

    WHERE { ?resource info:age ?age .

        FILTER (?age >= 24)}

    查询结果是:

    ------------------------------------------

    | resource                         | age |

    ==========================================

    | <http://somewhere/JohnSmith/>    | 44  |

    | <http://somewhere/RebeccaSmith/> | 30  |

    ------------------------------------------

     

    2.3 可选的查询信息optional information

    · 在一些查询中,一些需要返回的数据可能不存在,而这些不存在的数据所在的数据元素中有其他需要返回的信息,这时候就可以通过可选查询信息进行查询,比如:

    PREFIX vcard:   <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name ?age

    WHERE

    { ?person vcard:FN  ?name .

      OPTIONAL { ?person vcard:Age ?age }

    }

    这是要查询一些名字和年龄,但有些人没有年龄信息,也要返回名字。

    于是,OPTIONAL表示,模式{ ?person info:age ?age } 是可选的,不是必须满足的。

    这个查询的执行语句是

    sparql --data=vc-db-2.rdf --query=q-opt1.rq

    查询结果是

    -----------------------

    | name          | age |

    =======================

    | "Sarah Jones" |     |

    | "John Smith"  | 44  |

    | "Becky Smith" | 30  |

    | "Matt Jones"  | 18  |

    -----------------------

    如果去点关键字OPTIONAL,那么,查询的结果就是

    -----------------------

    | name          | age |

    =======================

    | "John Smith"  | 44  |

    | "Becky Smith" | 30  |

    | "Matt Jones"  | 18  |

    -----------------------

    有些人没有年龄信息,那么,这些人的名字也不会被作为查询结果返回。

    2.4 对可选模式添加过滤条件

    PREFIX vcard:      <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name ?age

    WHERE

    { ?person vcard:FN  ?name .

      OPTIONAL { ?person vcard:Age ?age . 

       FILTER ( ?age > 24 ) }

    }

    这样返回的信息是

    -----------------------

    | name          | age |

    =======================

    | "Sarah Jones" |     |

    | "John Smith"  | 44  |

    | "Becky Smith" | 30  |

    | "Matt Jones"  |     |

    -----------------------

    · 有些人没有年龄信息("Sarah Jones"),有些人的年龄小于24("Matt Jones" ),他们的名字信息也会出现在查询结果中。下面的查询要求,如果有年龄信息,那么年龄必须大于24,否则不是期望的查询结果。

    PREFIX vcard:<http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name ?age

    WHERE

    { ?person vcard:FN  ?name .

      OPTIONAL { ?person vcard:Age ?age . }

      FILTER ( !bound(?age) || ?age > 24 )

    }

    语句 !bound(?age) || ?age > 24  的意思是,没有(未绑定)age或者age大于24。如此,年龄小于24"Matt Jones"就不会出现在这个查询的结果中了。

    -----------------------

    | name          | age |

    =======================

    | "Sarah Jones" |     |

    | "John Smith"  | 44  |

    | "Becky Smith" | 30  |

    -----------------------

    2.5 联合查询

    · vCard词汇表和FOAF词汇表都可以表示人的信息,比如vCard中的vCard:FN, FOAF中的foaf:name.这一节介绍在一个RDF图同时用vCard:FN和foaf:name表示人的信息时,如何查询相关数据。

    注:vCard是电子商务中卡的一种文件格式标准,一般与邮件信息关联。FOAFhttp://xmlns.com/foaf/0.1/)是一种RDF的应用,所列网址有它的规范。

    · 一个RDF文件,r3.rdf文件的的内容为

    <?xml version="1.0"?>

    <rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"

      xmlns:foaf="http://xmlns.com/foaf/0.1/"

      xmlns:vCard="http://www.w3.org/2001/vcard-rdf/3.0#">

      <rdf:Description rdf:about="http://somewhere/MattJones">

        <foaf:name>Matt Jones</foaf:name>

      </rdf:Description>

      <rdf:Description rdf:about="http://somewhere/SarahJones">

        <foaf:name>Sarah Jones</foaf:name>

      </rdf:Description>

      <rdf:Description rdf:about="http://somewhere/BeckySmith/">

        <vCard:name>Becky Smith</vCard:name>

      </rdf:Description>

      <rdf:Description rdf:about="http://somewhere/JohnSmith/">

        <vCard:name>John Smith</vCard:name>

      </rdf:Description>

    </rdf:RDF>

    它只是分别用foaf:namevcard:FN描述了四个人名,这一节的查询将针对此文件。

    · 查询人名信息

    PREFIX foaf: <http://xmlns.com/foaf/0.1/>

    PREFIX vCard: <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name

    WHERE{

       { [] foaf:name ?name } UNION { [] vCard:FN ?name }

    }

    查询结果是

    -----------------

    | name          |

    =================

    | "Sarah Jones" |

    | "Matt Jones"  |

    | "John Smith"  |

    | "Becky Smith" |

    -----------------

    一个等价的查询语句是

    PREFIX foaf: <http://xmlns.com/foaf/0.1/>

    PREFIX vCard: <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name

    WHERE{

      [] ?p ?name 

      FILTER ( ?p = foaf:name || ?p = vCard:FN ) }

    · 记录结果的来源,查询语句和结果分别是

    PREFIX foaf: <http://xmlns.com/foaf/0.1/>

    PREFIX vCard: <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name1 ?name2

    WHERE{

       { [] foaf:name ?name1 } UNION { [] vCard:FN ?name2 }

    }

     

    ---------------------------------

    | name1         | name2         |

    =================================

    | "Sarah Jones" |               |

    | "Matt Jones"  |               |

    |               | "John Smith"  |

    |               | "Becky Smith" |

    --------------------------------- 

    使用OPTIONAL

    PREFIX foaf: <http://xmlns.com/foaf/0.1/>

    PREFIX vCard: <http://www.w3.org/2001/vcard-rdf/3.0#>

    SELECT ?name1 ?name2

    WHERE{

      ?x ?a ?name

      OPTIONAL { ?x  foaf:name  ?name1 } 

      OPTIONAL { ?x  vCard:FN   ?name2 }

    }

    查询结果是:

    ---------------------------------

    | name1         | name2         |

    =================================

    | "Matt Jones"  |               |

    | "Sarah Jones" |               |

    |               | "Becky Smith" |

    |               | "John Smith"  |

    ---------------------------------

     

    2.6 查询命名的图

    · 图是一个RDF数据集,不是一个完整的RDF文件。现在有三个图

    ds-dft.rdf

    <?xml version="1.0"?>

    <!DOCTYPE rdf:RDF [<!ENTITY xsd "http://www.w3.org/2001/XMLSchema#">]>

    <rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"

      xmlns:dc="http://purl.org/dc/elements/1.1/">

      <rdf:Description rdf:about="ds-ng-1.rdf">

        <dc:date rdf:datatype="&xsd;dateTime">2005-07-14T03:18:56+0100</dc:date>

      </rdf:Description>

      <rdf:Description rdf:about="ds-ng-2.rdf">

        <dc:date rdf:datatype="&xsd;dateTime">2005-09-22T05:53:05+0100</dc:date>

      </rdf:Description>

    </rdf:RDF>

    ds-ng-1.rdf

    <?xml version="1.0"?>

    <!DOCTYPE rdf:RDF [<!ENTITY xsd "http://www.w3.org/2001/XMLSchema#">]>

    <rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"

      xmlns:dc="http://purl.org/dc/elements/1.1/">

      <rdf:Description rdf:about="">

        <dc:title>Harry Potter and the Philospher's Stone</dc:title>

      </rdf:Description>

      <rdf:Description rdf:about="">

        <dc:title>Harry Potter and the Chamber of Secrets</dc:title>

      </rdf:Description>

    </rdf:RDF>

    ds-ng-2.rdf

    <?xml version="1.0"?>

    <!DOCTYPE rdf:RDF [<!ENTITY xsd "http://www.w3.org/2001/XMLSchema#">]>

    <rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"

      xmlns:dc="http://purl.org/dc/elements/1.1/">

      <rdf:Description rdf:about="">

        <dc:title>Harry Potter and the Sorcerer's Stone</dc:title>

      </rdf:Description>

      <rdf:Description rdf:about="">

        <dc:title>Harry Potter and the Chamber of Secrets</dc:title>

      </rdf:Description>

    </rdf:RDF>

    · 查询语句是

    PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>

    PREFIX dc: <http://purl.org/dc/elements/1.1/>

    PREFIX : <.>

    SELECT *{ ?s ?p ?o }

    对图的查询是(PREFIX : <.>是为了格式化输出???),

    sparql --graph=ds-dft.rdf --namedgraph=ds-ng-1.rdf --namedgraph=ds-ng-2.rdf --query=ds-dft.rq

    查询结果是

    ---------------------------------------------------------------------

    | s            | p       | o                                        |

    =====================================================================

    | :ds-ng-2.rdf | dc:date | "2005-09-22T05:53:05+0100"^^xsd:dateTime |

    | :ds-ng-1.rdf | dc:date | "2005-07-14T03:18:56+0100"^^xsd:dateTime |

    ---------------------------------------------------------------------

    · 查询指定图

    PREFIX dc: <http://purl.org/dc/elements/1.1/>

    PREFIX : <.>

    SELECT ?title{ 

      GRAPH :ds-ng-2.rdf

        { ?b dc:title ?title }}

    查询结果

    ---------------------------------------------

    | title                                     |

    =============================================

    | "Harry Potter and the Chamber of Secrets" |

    | "Harry Potter and the Sorcerer's Stone"   |

    ---------------------------------------------

    2.7 SPARQL查询结果集

    ·  四种形式的结果

    ■ SELECT – 返回一个表(table),Tutorial里介绍的主要是这种查询

    ■ CONSTRUCT –  返回一个RDF图

    ■ DESCRIBE – 返回一个RDF图. 

    ■ ASK –  布尔查询

    · 结果调整

    ■ Projection  - 投影- 只保持选择的变量

    ■ OFFSET/LIMIT - 偏移和限制 - 分解数字结果

    ■ ORDER BY  - 排序

    ■ DISTINCT - 产生只有一行的一个组合变量和值. 

  • 相关阅读:
    kafka 学习笔记
    awk命令详解
    apache 的 配置项
    Apache 的 httpd.conf 详解
    如何设置httpd-mpm-conf的参数
    apache 服务器概述--安装(一)
    centos 修改时区
    docker(三)docker镜像和镜像发布方法
    docker(二)部署docker容器虚拟化平台
    sql的存储过程使用详解--基本语法
  • 原文地址:https://www.cnblogs.com/linzhenjie/p/3139171.html
Copyright © 2011-2022 走看看