在 Perl 文档中,有一节关于 .postfix/.postcircumfix ,它说
In most cases, a dot may be placed before a postfix or postcircumfix:
my @a;
@a[1, 2, 3];
@a.[1, 2, 3]; # Same
Technically, not a real operator; it's syntax special-cased in the compiler.
我自己试过:
> my @a = 1,2,3,4,5
> @a[1] # 2
> @a.[1] # 2
> my %a = Perl => 6, Python => 3, PHP => 7
> %a<Perl> #6
> %a.<Perl> #6
> my @weekdays = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday'];
> @weekdays.antipairs.hash{'Sunday'} # 6, I expected it to be syntax wrong, but it did work!
> @weekdays.antipairs.hash.{'Sunday'} # 6, seems visual clarity or brevity
那么,Perl 6 中后缀或后缀前的点是什么意思?它到底是怎么做到的?我对此很好奇。谢谢。
最佳答案
Perl 6 中的表达式被解析为 termish
与 infixish
的事情他们之间的事情。一个 termish
依次定义为零个或多个 prefixish
事物,然后是术语本身,然后是零个或多个 postfixish
事物。 postfixish
包含所有:
.foo
)++
)[42]
中的 @a[42]
) >>
) 以将它们分布在数据结构中 由于它只查找零个或多个,因此您可以自由地交错方法调用以及散列和数组索引。这解释了为什么
@weekdays.antipairs.hash{'Sunday'}
解析很好(以及为什么 @weekdays.antipairs.hash<Sunday>
也可以工作,甚至 @weekdays.antipairs.hash<Sunday>.say
也很好)。至于
.
,语法简单地接受并忽略 .
之前 postfix
或 postcircumfix
.这是解析器的一个稍微简化的版本,我已经注释了一些以解释这些部分是什么。token postfixish {
<!stdstopper>
# If we're not in a string interpolation, allow unspace (that's
# where you write `\ ++`, for example, allowing spreading
# postfixish things over multiple lines).
[ <!{ $*QSIGIL }> [ <.unsp> | '\\' ] ]?
# Here we match the >> for doing a hyper. Note that it accepts
# but disregards a '.' before it. It's not captured at all and
# doesn't affect the code that is compiled.
[ ['.' <.unsp>?]? <postfix_prefix_meta_operator> <.unsp>?]**0..1
[
| <OPER=postfix>
# When there'd be no confusion with a method call, a '.' is
# also accepted and disregarded before a postfix operator
| '.' <?before \W> <OPER=postfix> ## dotted form of postfix operator (non-wordy only)
| <OPER=postcircumfix>
# Ditto here for recognized postcircumfixes
| '.' <?[ [ { < ]> <OPER=postcircumfix>
| <OPER=dotty>
| <OPER=privop>
]
}
因此
.
在这种情况下根本没有任何意义。解析器只是简单地接受它,然后继续寻找它当时真正关心的东西。另一件值得注意的事情是 postfix 和 postcircumfix 运算符也都在一个dotty 术语之后工作,在
$_
上运行。 .因此:my @xs = 1..10;
.++ for @xs;
say @xs;
将产生:
[2 3 4 5 6 7 8 9 10 11]
这是一个 postcircumfix 示例:
my %h = a => 1, b => 2, c => 3;
say .<a> + .<c> given %h;
产生
4
.Perl 6 语法通常旨在使代码从一种形式转移到另一种形式变得容易,并接受
.
在即使不是严格需要的地方,也可以稍微减轻一点(因此可以重构为 say %h1.<a> + %h2.<b>;
并且解析器会很好地处理它)。考虑 %h<a>
也可能有助于学习目的%h.<a>
的简称,这又会使 .<a> given %h
少一点惊喜。.
提供的额外空间也可能有助于清晰,特别是如果要堆叠多个后缀,甚至可以 - 如果语言扩展出于某种原因决定定义一些“有趣的”术语或后缀运算符 - 作为消除歧义的一种手段。
关于compilation - Perl 6 中后缀或后缀前的点是什么意思?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50189205/