在 Rakudo 的更新版本中,有一个名为的子集将UInt
其限制为正值。
class Wizard {
has UInt $.mana is rw;
}
这样,如果您需要这样的事情,您就不会陷入困境;这是定义的方式:(
您可以省略my
,但我想向您展示Rakudo 源代码的实际行)
my subset UInt of Int where * >= 0;
你也可以这样做:
class Wizard {
has Int $.mana is rw where * >= 0;
}
我想指出,* >= 0
in约束只是创建Callablewhere
的一种捷径。
您可以将以下任何一项作为where
约束:
... where &subroutine # a subroutine that returns a true value for positive values
... where { $_ >= 0 }
... where -> $a { $a >= 0 }
... where { $^a >= 0 }
... where $_ >= 0 # statements also work ( 「$_」 is set to the value it's testing )
(如果您希望它不为零,您也可以使用... where &prefix:<?>
它可能更好地拼写为... where ?*
or ... where * !== 0
)
如果您觉得使用您的代码的人很烦人,您也可以这样做。
class Wizard {
has UInt $.mana is rw where Bool.pick; # accepts changes randomly
}
如果您想在查看类中的所有值时确保该值“有意义”,那么您将不得不做更多的工作。
(它可能还需要更多的实现知识)
class Wizard {
has Int $.mana; # use . instead of ! for better `.perl` representation
# overwrite the method the attribute declaration added
method mana () is rw {
Proxy.new(
FETCH => -> $ { $!mana },
STORE => -> $, Int $new {
die 'invalid mana' unless $new >= 0; # placeholder for a better error
$!mana = $new
}
)
}
}