如何匹配至少包含三个单词且可能包含部分定界符的定界句子?
How can I match a delimited sentence that has at least three words and that may contain parts of delimiters?
我需要匹配一个由“,”或“::”分隔的字符串。
重要的是要注意句子本身可以包含“,”和“:”,并且我所说的句子是指至少两个单词和一个 space.
示例:
test.wav,,200,,This is a test, or is it?::test 2.wav,,test 3.wav::I said: Do not do that,,error.wav
预期输出:
[
{
"groups": [],
"match": "This is a test, or is it?"
},
{
"groups": [],
"match": "I said: Do not do that"
}
]
我试过:
1.
(?:,,|::)(?:[a-zA-Z0-9\.\-,?!;/\(\)]+\h){2,}.*?(?:,,|::)
但这给了我:
[
{
"groups": [],
"match": ",,200,,This is a test, or is it?::"
}
]
(?<=,,|::)(?:[a-zA-Z0-9\.\-,?!;/\(\)]+\h){2,}.*?(?:,,|::)
输出:
[
{
"groups": [],
"match": "200,,This is a test, or is it?::"
},
{
"groups": [],
"match": "test 2.wav,,test 3.wav::"
}
]
解决这个问题的正确方法是什么?
您可以将此正则表达式用于前瞻和后视条件:
(?<=,,|::)\h*(?:(?!\S*(?:,,|::))\S+\h+){3}.*?(?=::|,,)
正则表达式详细信息:
(?<=,,|::)
:正面回顾断言我们在当前位置 之前有,,
或::
\h*
: 匹配 0+ 个空格
(?:
: 开始non-capture组
(?!\S*(?:,,|::))
:否定前瞻断言我们不匹配 ::
或 ,,
作为下一个 non-whitespace 词 的一部分
\S+\h+
:匹配 1+ non-whitespace 字符串后跟 1+ 空格
){3}
: 结束non-capture组。匹配此组至少 3 次
.*?
:匹配0个或多个任意字符(non-greedy)
(?=::|,,)
:积极前瞻断言我们在当前位置 之后有,,
或::
您也可以使用模式来匹配至少 2 个后跟 space 的词,并至少匹配一个字符作为第三个不必后跟 [=43= 的词].
(?:,,|::)\h*\K(?:(?>[^\s,:]+|,(?!,)|:(?!:))+\h+){2,}(?:(?>[^\s,:]+|,(?!,)|:(?!:)))+(?=\h*(?:,,|::))
说明
(?:,,|::)\h*\K
匹配 ,,
或 ::
和可选的 spaces,然后忘记使用 \K
匹配的内容
(?:(?>[^\s,:]+|,(?!,)|:(?!:))+\h+){2,}
匹配至少一个不包含 ,,
或 ::
的字符的至少 2 个“单词”
(?:(?>[^\s,:]+|,(?!,)|:(?!:)))+
匹配不包含 ,,
或 ::
的至少一个字符的单词
(?=\h*(?:,,|::))
正面前瞻,断言可选的 space 后跟 ,,
或 ::
我需要匹配一个由“,”或“::”分隔的字符串。 重要的是要注意句子本身可以包含“,”和“:”,并且我所说的句子是指至少两个单词和一个 space.
示例:
test.wav,,200,,This is a test, or is it?::test 2.wav,,test 3.wav::I said: Do not do that,,error.wav
预期输出:
[
{
"groups": [],
"match": "This is a test, or is it?"
},
{
"groups": [],
"match": "I said: Do not do that"
}
]
我试过:
1.
(?:,,|::)(?:[a-zA-Z0-9\.\-,?!;/\(\)]+\h){2,}.*?(?:,,|::)
但这给了我:
[
{
"groups": [],
"match": ",,200,,This is a test, or is it?::"
}
]
(?<=,,|::)(?:[a-zA-Z0-9\.\-,?!;/\(\)]+\h){2,}.*?(?:,,|::)
输出:
[
{
"groups": [],
"match": "200,,This is a test, or is it?::"
},
{
"groups": [],
"match": "test 2.wav,,test 3.wav::"
}
]
解决这个问题的正确方法是什么?
您可以将此正则表达式用于前瞻和后视条件:
(?<=,,|::)\h*(?:(?!\S*(?:,,|::))\S+\h+){3}.*?(?=::|,,)
正则表达式详细信息:
(?<=,,|::)
:正面回顾断言我们在当前位置 之前有\h*
: 匹配 0+ 个空格(?:
: 开始non-capture组(?!\S*(?:,,|::))
:否定前瞻断言我们不匹配::
或,,
作为下一个 non-whitespace 词 的一部分
\S+\h+
:匹配 1+ non-whitespace 字符串后跟 1+ 空格
){3}
: 结束non-capture组。匹配此组至少 3 次.*?
:匹配0个或多个任意字符(non-greedy)(?=::|,,)
:积极前瞻断言我们在当前位置 之后有
,,
或::
,,
或::
您也可以使用模式来匹配至少 2 个后跟 space 的词,并至少匹配一个字符作为第三个不必后跟 [=43= 的词].
(?:,,|::)\h*\K(?:(?>[^\s,:]+|,(?!,)|:(?!:))+\h+){2,}(?:(?>[^\s,:]+|,(?!,)|:(?!:)))+(?=\h*(?:,,|::))
说明
(?:,,|::)\h*\K
匹配,,
或::
和可选的 spaces,然后忘记使用\K
匹配的内容
(?:(?>[^\s,:]+|,(?!,)|:(?!:))+\h+){2,}
匹配至少一个不包含,,
或::
的字符的至少 2 个“单词”
(?:(?>[^\s,:]+|,(?!,)|:(?!:)))+
匹配不包含,,
或::
的至少一个字符的单词
(?=\h*(?:,,|::))
正面前瞻,断言可选的 space 后跟,,
或::