perl6插值数组匹配AND,OR,NOT函数

lis*_*tor 8 arrays interpolation match perl6

我正在尝试重新执行我的程序以匹配所有,匹配任何匹配项目中的项目.关于Perl6的一些文档没有解释当前实现的行为(Rakudo 2018.04),我还有一些问题.

(1)关于正则表达式的文档说,将数组插入匹配正则表达式意味着"最长匹配"; 但是,这段代码似乎没有这样做:

> my $a="123 ab 4567 cde";
123 ab 4567 cde
> my @b=<23 b cd 567>;
[23 b cd 567]
> say (||@b).WHAT
(Slip)
> say $a ~~ m/ @b /
 ?23?    # <=== I expected the match to be "567" (@b[3] matching $a) which is longer than "23";
Run Code Online (Sandbox Code Playgroud)

(2)(|| @b)是Slip; 如何轻松地对数组中的所有元素进行OR或AND而不显式循环遍历数组?

> say $a ~~ m:g/ @b /
(?23? ?b? ?567? ?cd?)
> say $a ~~ m:g/ ||@b /
(?23? ?b? ?567? ?cd?)
> say $a ~~ m/ ||@b /
 ?23?
> say $a ~~ m:g/ |@b /
(?23? ?b? ?567? ?cd?)
> say $a ~~ m:g/ &@b /
(?23? ?b? ?567? ?cd?)
> say $a ~~ m/ &@b /
 ?23?
> say $a ~~ m/ &&@b /
 ?23?    # <=== && and & don't do the AND function
Run Code Online (Sandbox Code Playgroud)

(3)我最终做的是将我之前的代码压缩成两行:

my $choose = &any; # can prompt for choice of any, one, all, none here;
say so (gather { for @b -> $z { take $a ~~ m/ { say "==>$_ -->$z"; } <{$z}> /; } }).$choose;
Run Code Online (Sandbox Code Playgroud)

按预期输出为"真".但我希望有一个更简单的方法,没有"聚集 - 采取"和"为"循环.

非常感谢您的任何见解.

lisprog

rai*_*iph 4

\n

在 AND、OR、NOT 函数的匹配中插入数组

\n
\n

我不知道有什么比莫里茨的更好的解决方案了AND

\n

OR在下面介绍。

\n

编写NOT匹配标记列表的一种自然方法是使用前向断言或后向断言的否定版本,例如:

\n
my $a="123 ab 4567 cde";\nmy @b=<23 b cd 567>;\nsay $_>>.pos given $a ~~ m:g/ <!before @b> /;\n
Run Code Online (Sandbox Code Playgroud)\n

显示:

\n
(0 2 3 4 6 7 9 10 11 13 14 15)\n
Run Code Online (Sandbox Code Playgroud)\n

这是字符串 中not 23bcd、 或的 12 个匹配的位置,由下面的 s 行显示,它指向每个匹配的字符位置:567"123 ab 4567 cde"^

\n
my $a="123 ab 4567 cde";\n       ^ ^^^ ^^ ^^^ ^^^\n       0123456789012345\n
Run Code Online (Sandbox Code Playgroud)\n
\n

我正在尝试重新执行我的程序,以匹配数组中的所有项目、匹配任意项目、不匹配项目。

\n
\n

这些听起来像路口,而你问题的其余部分显然都是关于路口的。如果您链接到现有程序,可能会让我/其他人更容易看到您正在尝试执行的操作。

\n

(1)

\n

||@b匹配中最左边的匹配标记@b,而不是最长的匹配标记。

\n

|@b单个 写入|来匹配中的最长匹配标记@b。或者,更好的是,只写 plain @b,这是同一件事的简写。

\n

与任何其他匹配模式一样,这两种匹配模式 (|@b||@b) 都受正则表达式引擎工作方式的影响,如 Moritz 所简要描述的以及下面更详细的描述。

\n

当正则表达式引擎将正则表达式与输入字符串进行匹配时,它从正则表达式的开头和输入字符串的开头开始。

\n

如果无法匹配,它会跳过输入字符串中的第一个字符,放弃该字符,并假装输入字符串从第二个字符开始。然后它再次尝试匹配,从正则表达式的开头但输入字符串的第二个字符开始。它会重复此操作,直到到达字符串末尾或找到匹配项。

\n

根据您的示例,引擎无法在开始处匹配,但从第二个字符位置开始123 ab 4567 cde成功匹配。23所以它就完成了——并且567你的匹配模式中的 是无关紧要的。

\n

获得您期望的答案的一种方法:

\n
my $a="123 ab 4567 cde";\nmy @b=<23 b cd 567>;\n\nmy $longest-overall = \'\';\nsub update-longest-overall ($latest) {\n  if $latest.chars > $longest-overall.chars {\n    $longest-overall = $latest\n  }\n}\n\n$a ~~ m:g/ @b { update-longest-overall( $/ ) } /;\n\nsay $longest-overall;\n
Run Code Online (Sandbox Code Playgroud)\n

显示:

\n
\xef\xbd\xa2567\xef\xbd\xa3\n
Run Code Online (Sandbox Code Playgroud)\n

下面解释的使用:g

\n

(2)

\n

|@b或者||@b在主线代码中的含义与正则表达式中的含义完全无关。如您所见,|@b与 相同@b.Slip||@b意味着@b.Slip.Slip评估结果为@b.Slip.

\n

OR要对 的元素进行“并行”最长匹配模式获胜@b,请在正则表达式中@b写入(或|@b) 。

\n

OR要对 的元素执行“顺序”最左匹配模式获胜@b,请||@b在正则表达式中写入。

\n

到目前为止,我无法弄清楚在正则表达式中用于为数组添加前缀时做什么&和做什么。&&在我看来,有多个与它们的使用相关的错误。

\n

在您问题的某些代码中,您指定了副词:g。这指示引擎在找到匹配项时不会停止,而是跳过刚刚匹配的子字符串,并开始尝试在输入字符串中进一步匹配。

\n

(还有其他副词。:ex副词是最极端的。在这种情况下,当输入字符串中的给定位置有匹配时,引擎会尝试匹配正则表达式和输入中同一位置的任何其他匹配模式字符串。无论积累了多少个匹配项,它都会继续执行此操作,直到尝试了正则表达式和输入字符串中该位置的所有最后一个可能的匹配项。只有当它耗尽所有这些可能性时,它才会在输入中向前移动一个字符字符串,并再次尝试彻底匹配。)

\n

(3)

\n

我最好的镜头:

\n
my $a="123 ab 4567 cde";\nmy @b=<23 b cd 567>;\nmy &choose = &any;\nsay so choose do for @b -> $z {\n  $a ~~ / { say "==>$a -->$z"; } $z /\n}\n
Run Code Online (Sandbox Code Playgroud)\n