Raku中如何在sub MAIN中正确定义强制命名参数?
问题诱因
你的写法存在两个语法层面的位置错误,导致MAIN的CLI参数解析逻辑没有按预期生效:
- 类型约束位置错误:你写的
Int :p($parm)!把Int类型约束放在了命名参数的外层,CLI解析器无法识别到-p选项需要接收一个整数类型的值,于是按照默认的短选项规则,把不带值传入的-p直接解析为布尔真值True,完全绕过了你定义的Int类型约束。 - 必填标记的作用域错误:你附加的
!必填标记没有绑定到对外暴露的-pCLI选项上,解析器判定-p本身是可选参数、后面跟随的Int值也是可选内容,才会在用法提示里输出-p[=Int]的可选标记。
正确实现方法
把类型约束放到参数别名的括号内,同时将必填标记!直接跟在命名参数声明的末尾,让解析器正确识别参数的约束规则,正确代码如下:
sub MAIN(:p(Int $parm)!) { say "* parm=", $parm; }
你也可以用is required特质实现完全相同的效果,写法如下:
sub MAIN(:p(Int $parm) is required) { say "* parm=", $parm; }
验证效果
直接运行脚本不传任何参数时,用法提示会明确显示-p为必填项,不再有方括号包裹的可选标记:
$ raku test-par.raku Usage: test-par.raku -p=<Int>
如果只传-p不带具体整数值,会直接抛出类型错误提示,不会再默认赋值为True:
$ raku test-par.raku -p Your service passed a Bool where a Int was expected. Did you forget a value? in sub MAIN at test-par.raku line 1 Usage: test-par.raku -p=<Int>
传入合法参数时可正常运行:
$ raku test-par.raku -p=42 * parm=42
内容的提问来源于stack exchange,提问作者zentrunix
相关产品推荐
相关产品推荐

