Help language development. Donate to The Perl Foundation

Kind::Subset::Parametric zef:Kaiepi last updated on 2022-12-04

test.raku
use Kind::Subset::Parametric;

# Arrays don't type their elements by default:
my @untyped = 1, 2, 3;
say @untyped.^name; # OUTPUT: Array

# You can make it so they do by parameterizing Array:
my Int:D @typed = 1, 2, 3;
say @typed.^name; # OUTPUT: Array[Int:D]

# But you can't typecheck untyped arrays using these parameterizations:
say @typed ~~ Array[Int:D];   # OUTPUT: True
say @untyped ~~ Array[Int:D]; # OUTPUT: False

# So let's make our own array type that handles this using a parametric subset:
subset TypedArray of Array will parameterize -> ::T {
    proto sub check(Array) {*}
    multi sub check(Array[T] --> True) { }
    multi sub check(Array:U --> False) { }
    multi sub check(Array:D $topic) { so $topic.all ~~ T }
    &check
} where { !!! };

# Now they can both be typechecked:
given TypedArray[Int:D] -> \IntArray {
    say @typed ~~ IntArray;        # OUTPUT: True
    say @untyped ~~ IntArray;      # OUTPUT: True
    say <foo bar baz> ~~ IntArray; # OUTPUT: False
}