如何将Raku Grammar令牌固定匹配字符串末尾'as类型'并处理括号
修复后的Lambda表达式解析语法
以下是针对问题的修复方案,解决了嵌套括号解析和最终as匹配的问题:
use Grammar::Tracer; my @types = <i32 str>; # 根据实际需求调整支持的类型 my grammar Lambda { token TOP { <signature> <body> ' as ' <r-type> $ } rule signature { '|' <a-sig> [',' <b-sig>]? '|' } rule a-sig { 'a:' <a-type> } rule b-sig { 'b:' <b-type> } token body { '(' <expr> ')' } token expr { [ <-[()]> || '(' <expr> ')' ]* } token a-type { @types } token b-type { @types } token r-type { @types } } # 测试用例 say Lambda.parse("|a: i32, b: i32| (a + b) as i32"); say Lambda.parse("|a: str, b: i32| (a.len() as i32 + b) as i32");
关键修复点说明:
处理嵌套括号:
重新定义expr令牌,使用递归匹配逻辑[ <-[()]> || '(' <expr> ')' ]*,允许表达式内部包含任意层级的平衡括号,正确解析a.len()这类带括号的子表达式。固定最终
as匹配:
在TOP规则末尾添加$锚点,强制' as ' <r-type>必须匹配字符串的最后部分。结合令牌的贪婪匹配特性,解析器会优先匹配完整的body(包括内部所有内容,即使包含中间的as语句),确保只有末尾的as会被识别为返回类型声明。移除不必要的前瞻断言:
原body中的<?before ' as '>前瞻断言会导致提前终止匹配,现在移除后由TOP的末尾锚点控制匹配边界,避免误触发。
内容的提问来源于stack exchange,提问作者librasteve
相关产品推荐
相关产品推荐

