这个新问题是我的后续问题previous https://stackoverflow.com/questions/69066403/how-can-raku-mixins-work-with-operator-overloading当我充实事情时,这一点就出现了。请注意,我也做了一些研究,并且有意识地避开提到的 Scalar Mixins bughere https://stackoverflow.com/questions/50590224/cannot-assign-to-immutable-value-when-trying-to-assign-to-a-string-role/50593692#50593692。因此,我将角色混合到对象中,而不是标量容器中。
大局是进行数学运算,同时也执行简单的误差计算。
这是我的失败代码的简洁版本:
1 role Error {
2 has $.abs-error
3 }
4
5 multi prefix:<-> ( Error:D $x ) is default {
6 # - $x; # fails - enters an infinite loop
7 # - $x.Real; # fails - does not drop the Error mixin
8 ( 0 - $x ) does Error($x.abs-error) # works - but relies on the infix:<-> form
9 }
10
11 my $dog = 12.5 does Error(0.5);
12
13 #what i have...
14 say $dog; #12.5
15 say $dog.WHAT; #(Rat+{Error})
16 say $dog.abs-error; #0.5
17
18 #what i want...
19 say (-$dog); #-12.5
20 say (-$dog).WHAT; #(Rat+{Error})
21 say (-$dog).abs-error; #0.5
我的问题的核心是:
- 作为 $dog 我的用户can获取第 14 行变量 (12.5) 的值
- 那么我怎样才能在第 7 行附近获得朴素的价值呢?
我尝试了(拼命?)一些事情:
- 强制转换为 Real (仍然得到混合对象)
- 分配给 Real 容器(允许 Rat+{Error} ~~ Real)
- $dog.default => 对于“Rat+{Error}”类型的调用者,没有这样的方法“默认”
谢谢大家的建议!!
对这个问题的直接回答是:不,没有任何操作可以撤销 mixin。但是,您可以采取一些技巧来实现原始类型的功能:
- 在方法重写的情况下,使用
$obj-with-mixin.OriginalType::method-name()
表单来调用已被覆盖的方法。
- 如果是
multi
sub(例如运算符),你可以这样做&prefix:<->.cando(\(1.5)).head
解决,但不调用,实施-
on Rat
,然后直接调用。
看看这个问题和你的前一个 https://stackoverflow.com/questions/69066403/how-can-raku-mixins-work-with-operator-overloading然而,似乎你每一步都在与语言作斗争;is default
确实是最后的手段,即使你可以使用 mixin 方法让它工作,你也会发现结果非常慢,很大程度上是因为 mixin 触发了去优化(从专门的和 JIT 编译的代码中掉出来,回到原来的状态)口译员)。
也许可以探索使用组合的设计:
# An object holding the value and the error.
class Error does Real {
has Real $.value;
has Real $.abs-error;
multi method Real(Error:D:) { $!value }
multi method gist(Error:D:) { "$!value±$!abs-error" }
}
# A cute constructor of this type, just for fun.
multi infix:<±>(Real $value, Real $abs-error) {
Error.new(:$value, :$abs-error)
}
# Negation; no `is default` or other tricks required!
multi prefix:<->(Error $e --> Error) {
Error.new(value => -$e.value, abs-error => $e.abs-error)
}
# It works!
my $x = 4.5 ± 0.1;
say $x;
say -$x;
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)