如何在含变音符号的SPARQL查询中正确使用正则表达式?
SPARQL正则匹配含变音符号资源的问题解决
我执行SPARQL查询筛选英文标签中包含"Sigmund"(大小写不敏感)的资源,但返回结果不完整,缺失了带变音符号的资源(比如Sigmund Jähn)。
原查询代码
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#> SELECT DISTINCT ?s WHERE { ?s rdfs:label ?label . FILTER ( LANG(?label) = "en" ) BIND (STR(?label) AS ?label_text) FILTER(REGEX(?label_text, "Sigmund", "i")) }
问题分析
缺失的核心原因是Unicode字符表示形式不一致:变音符号(比如ä)在DBpedia的标签中可能存在两种等价但编码不同的形式:
- 单一合成字符(如U+00E4,直接的ä)
- 分解形式(如U+0061字母a + U+0308组合分音符)
原查询直接对原始字符串做正则匹配,无法识别这两种等价的Unicode编码,导致带分解形式变音符号的资源被过滤。
解决方法
使用UNICODE_NORMALIZE函数将标签字符串归一化为标准合成形式(NFC),确保等价的Unicode字符统一为相同的编码表示,再执行正则匹配:
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#> SELECT DISTINCT ?s WHERE { ?s rdfs:label ?label . FILTER ( LANG(?label) = "en" ) # 将字符串归一化为标准合成形式NFC,统一等价字符编码 BIND (UNICODE_NORMALIZE(STR(?label), "NFC") AS ?normalized_label) FILTER(REGEX(?normalized_label, "Sigmund", "i")) }
补充说明
UNICODE_NORMALIZE支持四种归一化形式:NFC、NFD、NFKC、NFKD,这里选择NFC(标准合成形式)即可覆盖绝大多数场景。- 也可以用
CONTAINS替代REGEX(先归一化再转小写),实现相同效果:FILTER(CONTAINS(LCASE(?normalized_label), "sigmund"))
内容的提问来源于stack exchange,提问作者Adrian Graap
相关产品推荐
相关产品推荐

