基于疫情数据的知识图谱问答系统(上)

该项目是我的一次课程设计,开发的语言是python。从网上学习了各种相关知识后写出的一个KBQA系统,希望这个系统的搭建过程也能给读者一些有用的经验。

一,数据获取

知识图谱的数据一般是非结构性的,获得的渠道有多种,如利用爬虫工具爬取相关的文本等等。

这里,我们构建图谱所需的疫情数据从OpenKg中文开放知识图谱获取

图谱中涉及到的知识有医生,救护人员以及他们的信息,履历,事迹。虽然样本量不大,但是对于数据所需的处理也比较繁琐。

新冠开放知识图谱.英雄 .

相关图片
JSON文件中存储了所需要的数据,这些数据是结构化的
在这里插入图片描述

数据说明

通过下载得来的schema文件可以发现,JSON文件中的数据包括22个类别,和48个属性节点。
概念:21个
实例:747个
数值属性:291个
对象属性:1160个
类别Class: people,school,institutions,battle,countries,field…

属性Property: nativePlace,gender,deathTime,birthDate,national…

二,关系抽取

要获得构建制图图谱系统所需的三元组数据,需要对以获取的数据,进行节点和关系边的提取。在这里,主要建立类别与属性之间的关系边。

提取节点和属性用的代码,由于这部分代码的重复性片段较多,因此展示了具有代表性操作的代码片段:

        with open(filename, encoding='utf-8') as f:
            #用于存储节点的列表的定义
            characterjson = json.load(f)
            characterlist=[]
            articlelist=[]
            institutionlist=[]
            teamlist=[]
        for data in characterjson['@graph']:
            #team_dict   救援队类节点的提取 
            if (data['@type'] == "http://www.openkg.cn/COVID-19/character/class/C548"):
                team.append(data['label']['@value'])
                team_dict = {}
                team_dict['team'] = data['label']['@value']
                teamlist.append(team_dict)

                if 'P45' in data:
                    team_dict['supportSite'] = data['P45']

                if 'P49' in data:
                    team_dict['departureDate'] = data['P49']
                    departureDate.append([data['label']['@value'], data['P49']])


            #institution dict   救助机构类节点的提取
            if (data['@type'] == "http://www.openkg.cn/COVID-19/character/class/C3"):
                institutions.append(data['label']['@value'])
                institution_dict = {}
                institution_dict['institution'] = data['label']['@value']
                institutionlist.append(institution_dict)
                if 'P24' in data:
                    institution_dict['cities'] = data['P24']

                if 'P25' in data:
                    institution_dict['To_enact'] = data['P25']
                if 'P26' in data:
                    institution_dict['publish'] = data['P26']

        #相关关系边的提取
        for data in characterjson['@graph']:
            if (data['@type'] == "http://www.openkg.cn/COVID-19/character/class/C1"):
                for i in characterlist:
                   if 'colleagues' in i:
                     if type(i['colleagues']) is list:
                       for j in range(len(i['colleagues'])):
                         if(data['@id']==i['colleagues'][j]):

                            i['colleagues'][j]=data['label']['@value']
                            colleagues.append([i['people'],data['label']['@value']])

                            break
                     else :
                         if (data['@id'] == i['colleagues']):

                             i['colleagues'] = data['label']['@value']
                             colleagues.append([i['people'], data['label']['@value']])

                             break

将所有的节点和关系边提取到列表后,可以用set()函数来去除重复的节点后将其存储起来。

三,数据库连接与使用

Neo4j 数据库

Neo4j数据库是存储图数据最常用的数据库之一,他的优点很明显。
1.与Python交互方便
2.容易上手,应用方便。
3.数据存储容量大,可输出结构化数据文件。
在这里插入图片描述

通过py2neo来链接与操作数据库

from py2neo import Graph,Node
class CharacterGraph:
    def __init__(self):
        self.data_path = './data/character-covid-19-v0.2.json'
        self.g = Graph(
            host="127.0.0.1",
            http_port=7474,
            user="neo4j",
            password="123456")
    def create_node(self, label, nodes):
        for node_name in nodes:
            node = Node(label, name=node_name)
            self.g.create(node)
        return
    def create_relationship(self, start_node, end_node, edges, rel_type, rel_name):
        set_edges = []
        for edge in edges:
            set_edges.append('###'.join(edge))
        for edge in set(set_edges):
            edge = edge.split('###')
            p = edge[0]
            q = edge[1]
            query = "match(p:%s),(q:%s) where p.name='%s'and q.name='%s' create (p)-[rel:%s{name:'%s'}]->(q)" % (start_node, end_node, p, q, rel_type, rel_name)
            try:
                self.g.run(query)
            except Exception as e:
                print(e)
        return

Neo4j生成相应的节点和关系边

在这里插入图片描述

至此,我们已经完成了对数据的处理与存储了,对于搭建一个KBQA系统来说,工作已经完成了一半了,在下一篇文章,我将会展示问答系统的搭建流程。

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值