You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

VS Code自定义语法高亮仅高亮每行首个数字/关键字如何解决

VS Code自研编程语言语法高亮扩展每行仅第一个关键字/数字高亮问题

我正在为自研的编程语言开发Visual Studio Code语法高亮扩展,期望所有符合规则的关键字都能被高亮,但目前每行仅第一个匹配的关键字会被高亮,效果如下图所示(图中所有单词均应被高亮):
关键字高亮效果
数字的高亮也存在相同问题:
数字高亮效果
以下是我的<language name>.tmLanguage.json配置内容:

{
    "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json",
    "name": "Language Name",
    "patterns": [
        {
            "include": "#control_keywords"
        },
        {
            "include": "#declaration_keywords"
        },
        {
            "include": "#double_quoted_strings"
        },
        {
            "include": "#single_quoted_strings"
        },
        {
            "include": "#hexadecimal_numbers"
        },
        {
            "include": "#octal_numbers"
        },
        {
            "include": "#binary_numbers"
        },
        {
            "include": "#decimal_numbers"
        },
        {
            "include": "#line_comments"
        },
        {
            "include": "#block_comments"
        }
    ],
    "repository": {
        "control_keywords": {
            "name": "keyword.control.language_name",
            "match": "\\b(if|while|for|return|continue|break|else)\\b"
        },
        "declaration_keywords": {
            "name": "keyword.declaration.language_name",
            "match": "\\b(fn|let|const)\\b"
        },
        "double_quoted_strings": {
            "name": "string.quoted.double.language_name",
            "begin": "\"",
            "end": "\"",
            "patterns": [
                {
                    "name": "constant.character.escape.language_name",
                    "match": "\\\\(\\\\|'|\"|n)"
                }
            ]
        },
        "single_quoted_strings": {
            "name": "string.quoted.single.language_name",
            "begin": "'",
            "end": "'",
            "patterns": [
                {
                    "name": "constant.character.escape.language_name",
                    "match": "\\\\(\\\\|'|\"|n)"
                }
            ]
        },
        "hexadecimal_numbers": {
            "name": "constant.numeric.hexadecimal",
            "match": "\\b0x[0123456789ABCDEFabcdef]*(\\.[0123456789ABCDEFabcdef]*)?\\b"
        },
        "octal_numbers": {
            "name": "constant.numeric.octal",
            "match": "\\b0o[01234567]*(\\.[01234567]*)?\\b"
        },
        "binary_numbers": {
            "name": "constant.numeric.octal",
            "match": "\\b0b[01]*(\\.[01]*)?\\b"
        },
        "decimal_numbers": {
            "name": "constant.numeric.decimal",
            "match": "\\b[0123456789]*(\\.[0123456789]*)?\\b"
        },
        "line_comments": {
            "name": "comment.line.double-slash",
            "match": "//[^\\n]*\n"
        },
        "block_comments": {
            "name": "comment.block",
            "begin": "/\\*",
            "end": "\\*/",
            "patterns": [
                {
                    "include": "#block_comments"
                }
            ]
        }
    },
    "scopeName": "source.language_name"
}

请问该如何修改配置才能实现每行多个匹配项均被高亮的效果?


解决方案

这个问题的核心原因是数字匹配规则存在正则缺陷,干扰了全局匹配逻辑:所有数字规则里的*量词允许匹配0个字符,会命中单词之间的空内容,导致匹配指针跳转异常,跳过后续的关键词匹配。此外还有几个细节错误也会影响匹配效果。

你需要做以下修改:

  1. 把所有数字匹配规则里的*替换为+,确保至少匹配1个数字,避免匹配空内容
  2. 修正二进制数字的scope名称错误,把constant.numeric.octal改成constant.numeric.binary
  3. 调整行注释的匹配规则,用$匹配行尾,避免显式匹配换行符导致的指针问题

修改后的完整配置如下:

{
    "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json",
    "name": "Language Name",
    "patterns": [
        {
            "include": "#control_keywords"
        },
        {
            "include": "#declaration_keywords"
        },
        {
            "include": "#double_quoted_strings"
        },
        {
            "include": "#single_quoted_strings"
        },
        {
            "include": "#hexadecimal_numbers"
        },
        {
            "include": "#octal_numbers"
        },
        {
            "include": "#binary_numbers"
        },
        {
            "include": "#decimal_numbers"
        },
        {
            "include": "#line_comments"
        },
        {
            "include": "#block_comments"
        }
    ],
    "repository": {
        "control_keywords": {
            "name": "keyword.control.language_name",
            "match": "\\b(if|while|for|return|continue|break|else)\\b"
        },
        "declaration_keywords": {
            "name": "keyword.declaration.language_name",
            "match": "\\b(fn|let|const)\\b"
        },
        "double_quoted_strings": {
            "name": "string.quoted.double.language_name",
            "begin": "\"",
            "end": "\"",
            "patterns": [
                {
                    "name": "constant.character.escape.language_name",
                    "match": "\\\\(\\\\|'|\"|n)"
                }
            ]
        },
        "single_quoted_strings": {
            "name": "string.quoted.single.language_name",
            "begin": "'",
            "end": "'",
            "patterns": [
                {
                    "name": "constant.character.escape.language_name",
                    "match": "\\\\(\\\\|'|\"|n)"
                }
            ]
        },
        "hexadecimal_numbers": {
            "name": "constant.numeric.hexadecimal",
            "match": "\\b0x[0123456789ABCDEFabcdef]+(\\.[0123456789ABCDEFabcdef]+)?\\b"
        },
        "octal_numbers": {
            "name": "constant.numeric.octal",
            "match": "\\b0o[01234567]+(\\.[01234567]+)?\\b"
        },
        "binary_numbers": {
            "name": "constant.numeric.binary",
            "match": "\\b0b[01]+(\\.[01]+)?\\b"
        },
        "decimal_numbers": {
            "name": "constant.numeric.decimal",
            "match": "\\b[0123456789]+(\\.[0123456789]+)?\\b"
        },
        "line_comments": {
            "name": "comment.line.double-slash",
            "match": "//.*$"
        },
        "block_comments": {
            "name": "comment.block",
            "begin": "/\\*",
            "end": "\\*/",
            "patterns": [
                {
                    "include": "#block_comments"
                }
            ]
        }
    },
    "scopeName": "source.language_name"
}

修改后重新加载扩展即可实现同一行多个关键词、数字的高亮效果。


内容的提问来源于stack exchange,提问作者astroide

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.04 10:36:03