This question was originally posted by lookatme
in the Perl6 IRC channel. The original intention is to constrain a Callable by using subsets or any other possible way. It works in signatures, however this:
subset WalkCb of Callable where *.signature ~~ :(Int $a);
my WalkCb $x = sub (Int $a) { return $a; };
returns
«Type check failed in assignment to $x; expected WalkCb but got Sub (sub (Int $a) { #`(Sub...) in block <unit> at <tmp> line 1»
Other variants of the declaration return similar messages. What would be the correct syntax?
A where
constraint can take a block (lambda) or a statement.
… where { $_ == 42 }; # block
… where * == 42; # lambda
… where $_ == 42; # statement
The thing is that ~~
doesn't participate in the creation of WhateverCode lambdas (*
)
So what you are really doing is creating a lambda of *.signature
inside of a larger where
statement (not lambda).
constant $lambda = *.signature;
subset WalkCb of Callable where $lambda ~~ :(Int $);
Which will of course never return True
as the lambda has a signature of :(;; $ is raw)
So instead just write the statement form. (using implicit $_
)
subset WalkCb of Callable where .signature ~~ :(Int $);
my WalkCb $x = sub (Int $a) { return $a }
say $x(42); # 42
It appears the WhateverCode
parsing messes up in this case. So if you specify a block in the where
:
subset WalkCb of Callable where { .signature ~~ :(Int $) }
my WalkCb $x = sub (Int $a) { return $a; }
it appears to work as expected. Also note that I removed the ;
at the end of the lines, as a }
at the end of a line is also the end of a statement. And that I removed the "a" from the signature: the name of of positional parameters in signature smartmatching is ignored.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With