3、金融数据源分析:结构化数据、半结构化数据、非结构化数据

做金融知识图谱,第一步不是写代码,而是搞清楚数据从哪来、长什么样。

我见过不少团队,一上来就急着建图,结果数据源没摸透,后面清洗、对齐、融合全崩了。说白了,数据源分析是地基,地基不稳,楼盖得再高也得塌。

3.1 结构化数据:数据库表里的“规矩人”

结构化数据,就是那种规规矩矩躺在关系型数据库里的表。比如MySQL、Oracle、PostgreSQL里的交易流水、客户信息、持仓明细。

这类数据最大的特点:模式固定、字段明确、类型清晰。每一行是一条记录,每一列是一个属性。

典型场景:银行核心系统的客户表(customer)、交易表(transaction)、账户表(account)。

举个例子,一张简单的交易表长这样:

-- 交易流水表结构示例
CREATE TABLE transaction (
    trans_id      VARCHAR(32) PRIMARY KEY,   -- 交易ID
    cust_id       VARCHAR(16),               -- 客户ID
    account_no    VARCHAR(20),               -- 账号
    trans_type    VARCHAR(8),                -- 交易类型(存款/取款/转账)
    trans_amount  DECIMAL(18,2),             -- 交易金额
    trans_time    DATETIME,                  -- 交易时间
    counterparty  VARCHAR(64)                -- 对手方
);

这种数据,我习惯直接做ETL映射。字段名和知识图谱的实体属性基本一一对应。比如cust_id映射成客户IDtrans_amount映射成交易金额

我的经验:结构化数据虽然“干净”,但别忘了检查主键唯一性、外键关联完整性。我曾经遇到过一个项目,客户表的主键居然有重复,导致图谱里出现了两个一模一样的“张三”。排查了整整两天。

3.2 半结构化数据:JSON/XML里的“自由灵魂”

半结构化数据,说白了就是有结构但不强制。JSON和XML是金融领域最常见的两种。

这类数据常见于API接口返回、日志文件、配置信息。比如交易所的行情快照、风控系统的规则配置、第三方支付的回调通知。

JSON示例:

{
  "event_id": "EVT20240315001",
  "event_type": "market_snapshot",
  "timestamp": "2024-03-15T09:30:00Z",
  "data": {
    "symbol": "600519.SH",
    "last_price": 1685.00,
    "volume": 1234567,
    "bid": [{"price": 1684.50, "size": 100}, {"price": 1684.00, "size": 200}],
    "ask": [{"price": 1685.50, "size": 150}, {"price": 1686.00, "size": 180}]
  }
}

XML示例(常见于银行间报文):

<?xml version="1.0" encoding="UTF-8"?>
<PaymentOrder>
  <OrderId>PO202403150001</OrderId>
  <Payer>
    <Name>某资产管理公司</Name>
    <Account>6222021234567890</Account>
  </Payer>
  <Payee>
    <Name>某证券公司</Name>
    <Account>6222020987654321</Account>
  </Payee>
  <Amount currency="CNY">5000000.00</Amount>
  <Purpose>债券交割款</Purpose>
</PaymentOrder>

处理半结构化数据,我常用的套路是:

  • 先做Schema推断:用工具(比如Spark的inferSchema)自动识别嵌套结构
  • 再拍平(Flatten):把嵌套的JSON/XML展开成扁平的表结构
  • 最后做字段映射:把拍平后的字段对齐到图谱的实体属性

避坑指南:我曾经处理过一份XML报文,里面嵌套了7层,而且同一层级的字段名在不同报文里还不一样(比如有的叫PayerName,有的叫Payer_Name)。这种“同名不同命”的情况,必须写专门的解析规则,不能偷懒用通用解析器。

3.3 非结构化数据:研报、新闻、公告里的“金矿”

非结构化数据,才是金融知识图谱真正的价值所在。为什么?因为结构化数据只能告诉你“谁干了什么”,而非结构化数据能告诉你“为什么”以及“接下来会怎样”。

常见的非结构化数据源包括:

  • 券商研报:行业分析、个股推荐、宏观策略
  • 财经新闻:实时快讯、深度报道、政策解读
  • 上市公司公告:年报、季报、重大事项、关联交易
  • 监管文件:处罚决定、问询函、政策法规

这类数据没有固定格式,全是自然语言文本。想从中提取知识,得靠NLP技术。

我一般分三步走:

  1. 实体识别(NER):找出文本里的公司名、人名、产品名、金额、日期等
  2. 关系抽取(RE):判断实体之间的关系,比如“A公司收购了B公司”、“C产品由D公司研发”
  3. 事件抽取:识别完整的事件,比如“某公司发布业绩预增公告”、“某行业出台新监管政策”

举个例子,一段新闻文本:

"2024年3月15日,某知名券商发布研报,给予某科技公司'买入'评级,目标价上调至50元。"

经过NLP处理后,可以抽取出:

实体类型 实体值
机构 某知名券商
公司 某科技公司
评级 买入
目标价 50元
日期 2024-03-15

这些信息就可以直接注入知识图谱,形成“券商-发布-研报-涉及-公司-获得-评级”这样的关联路径。

我的经验:非结构化数据里,研报的质量最高,但噪声也最大。有些研报通篇都是“我们认为”、“我们预计”,真正有信息量的句子可能只占20%。我习惯先用规则过滤掉模板化的废话,再交给NLP模型处理。这样能省下不少算力。

3.4 三类数据源的知识图谱融合逻辑

三类数据源不是孤立的。在实际项目中,它们需要融合到同一个知识图谱里。

我画了一张图,帮你理清这个逻辑:

金融知识图谱数据源融合架构 结构化数据 数据库表 交易流水、客户信息 字段映射 → 实体属性 半结构化数据 JSON / XML 行情快照、报文 拍平 → 字段映射 非结构化数据 研报、新闻、公告 NLP抽取实体关系 事件抽取 数据融合层 实体对齐、关系融合、冲突消解、时间戳对齐 金融知识图谱

你看,三类数据源经过各自的预处理后,统一进入融合层。在这里,我们要做几件关键的事:

  • 实体对齐:比如结构化数据里的“某科技公司”和非结构化数据里提到的“某科技公司”,是不是同一个实体?需要靠名称匹配、ID映射、甚至语义相似度来判断。
  • 关系融合:同一个关系可能从多个数据源里提取出来,比如“收购”关系,既可能来自公告文本,也可能来自交易流水。需要合并去重。
  • 冲突消解:不同数据源对同一实体的属性描述可能不一致。比如结构化数据里某公司注册资本是1亿,但新闻里写的是1.2亿。这时候需要根据数据源的权威性、时效性来决定用哪个。
  • 时间戳对齐:金融数据对时间极其敏感。同一个事件在不同数据源里的时间戳可能差几秒甚至几天,必须统一到同一个时间轴上。

一个小技巧:我习惯在融合层保留数据源的“血缘信息”。也就是每个实体、每个关系都打上来源标签(比如“来自交易表”、“来自2024年3月15日新闻”)。这样后期排查问题时,能快速定位数据源头。

嗯,数据源分析这块,说白了就是搞清楚“有什么、怎么用、怎么合”。把这三类数据吃透了,知识图谱的构建就成功了一半。


公众号:蓝海资料掘金营,微信deep3321