提问者:小点点

有没有一种直接的方法来检查某样东西是否是混合的?


Raku mixins有两个(或更多)性质,在同一个容器中组合多个值,或者与角色一起组合值。然而,据我所知,没有一种直接的方法来检查非您创建的变量中的“混合性”。

这可能是个诡计

my $foo = 3 but Stringy;
say $foo.^name ~~ /\+/;# OUTPUT: «「+」␤»

但是有没有其他我遗漏的财产可以直接查这个?


共3个答案

匿名用户

我认为您缺少^角色^父母元方法:

my $foo = 3 but Stringy;
dd $foo.^roles;   # (Stringy, Real, Numeric)
dd $foo.^parents; # (Int,)

匿名用户

太长别读我的不可靠的解决方案[1]比你的不可靠的解决方案[2]更简单,更快,并且应该适用于问题Y和问题X[3]

sub is-mixin ($object) { $object.^is_mixin =:= 1 }
say is-mixin 3;           # False
say is-mixin 3 but 'bar'; # True

[1]"警告:[角色元模型::Mixins]是Rakudo实现的一部分,而不是语言规范的一部分。"

[2]我没有搜索roast,但会想象在类型名称中使用只是一种约定,而不是语言规范的一部分。

[3]我发现你的问题是XY问题的一个例子,根据我下面的第一条评论;和/或术语混淆,根据我的第二个。这个答案的其余部分解释了我的意思。

有没有一种直接的方法来检查容器是否是混合容器?

“容器”一词在Raku中具有技术含义。它指的是遵循Raku容器协议的值。当值后跟=以调用“赋值”时,容器协议适用。

你所问的似乎与这样一个容器无关,因为它不同于一个值。有充分的理由认为这对你来说并不重要——你感兴趣的只是测试一个值是否是一个混合元素,而“容器”方面是一个转移注意力的东西,要么是因为你不是在Raku中通常意义上的“容器”,要么是因为它无关紧要,因为容器是一个值,所以无论什么用于测试一个值都会用于测试一个容器。

例如,看看你的“把戏”:

my $foo = 3 but Stringy;
say $foo.^name ~~ /\+/;# OUTPUT: «「+」␤»

这个技巧与使用Raku中“容器”一词的正常技术用法的任何容器方面无关。如果您编写以下不涉及容器的内容,您将获得相同的结果:say(3但Stringy)。^name ~~ /\ /;# OUTPUT: «「 」␤»

所以在我的解决方案中,我假设你只是指一个值,知道你的最终焦点是否在一个容器上实际上并不重要。

如果我的假设是错误的,这会有所不同,我敦促你解释你想做什么的X,而不仅仅是Y。

匿名用户

你的把戏让你的代码变得脆弱,因为它不期望

$foo.^set_name('The Spanish Inquisition');

当然没有人这样做:)

你最好问问Rakudo元模型:

say $foo.^is_mixin; # OUTPUT: «1␤»

需要注意两件事:

  1. is_mixin元方法不会返回Bool
  2. name元方法一样,它特定于Raku
  3. 的Rakudo实现