如何用Lua模式匹配含可选平衡大括号的字符串?
如何用Lua匹配包含可选平衡大括号的逗号分隔项
刚好碰到过类似的问题!首先得明确:Lua的原生模式匹配里,%b{}是个特殊的模式单元,它专门匹配一对平衡的括号结构,但你没法直接给它加?来让整个括号结构变成可选——因为?在Lua模式里只能修饰单个字符,或者用()括起来的字符组,而%b{}本身不属于可分组修饰的范畴,所以[^,]-%b{}?这种写法完全达不到你想要的效果。
先看你的初始尝试:
for m in string.gmatch('str{},str2{str3{}},str4,str5{a{}b{}}', '[^,]-%b{}') do print(m) end
(哦对了,你代码里写的print(v)应该是笔误,应该是print(m))
这个模式只会抓取必须包含平衡大括号的项,所以str4这种完全没有括号的项自然就被漏掉了。
那能不能用单一的原生Lua模式实现需求?很可惜,Lua的模式系统没有那么强大,它不支持递归匹配或者复杂的分组可选逻辑,所以没法用一行模式串直接搞定这个场景。
不过你的临时解决方案思路非常靠谱——先按逗号拆分片段,再处理可能被拆分的不平衡括号:
local str = 'str{},str2{str3{}},str4,str5{a{}b{}}' local stored for e in string.gmatch(str, '[^,]+') do if stored then e = stored .. ',' .. e end -- 检查是否是无括号项,或者包含完整平衡括号的项 if string.match(e, '^[^{}]+$') or string.match(e, '^[^{}]*%b{}[^{}]*$') then print(e) stored = nil else stored = e end end
这段代码的核心逻辑是:
- 先把字符串按逗号拆分成最小片段
- 如果之前有暂存的、括号不平衡的片段,就把当前片段拼回去(处理被逗号拆分的括号结构)
- 检查拼接后的内容:要么完全没有括号,要么包含完整的平衡括号(且括号前后没有未闭合的部分)
- 符合条件就输出,否则暂存起来等下一次拼接
这个方案能完美覆盖所有情况:既不会漏掉str4这种无括号项,也能正确识别嵌套平衡括号的项,同时不会错误输出未闭合的括号片段。
内容的提问来源于stack exchange,提问作者HenrikD
相关产品推荐
相关产品推荐

