Skip to content
This repository


Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
tree: 05514649c3
Fetching contributors…


Cannot retrieve contributors at this time

file 279 lines (206 sloc) 9.446 kb


perltypes - Perl type system


Dynamic types


Types in lexical variables

Perl optionally allows storing the type, i.e. an existing package name, in the declaration of lexical variables. Lexicals are stored in pads, the package name, i.e. the type, is stored in the comppad_name slot for each pad. Up to version 5.18 Perl did not use these types for checks and optimizations, only external modules did.

Remember: A type is implemented as package. A valid type must be an existing and loaded package.

Global variables can not store types.


With use coretypes Perl allows strict types of int, double and string, which can be applied to scalars, arrays and hashes. TODO: functions not yet. This would be the return type.

Any type change for those strictly typed variables will be detected at compile-time and if this fails at run-time. The type int is interpreted as IV, double as NV and string as PV only. There is no stringification for IV and NV, no magic such as "tie" in perlfunc, no setting to undef allowed.


"const" in perldata is a new type qualifier for lexical variables to enable compile-time readonly and assignment checks and type optimizations. You must assign a value within the declaration.

  my const $a = 0;
  my const($b,$c) = (0,1);
  my (const $d, $free) = (0,1);
  my (const int $i, const string $s) = (0,"1");

const sets the internal SVf_READONLY flag for the variable, if it's a scalar, array or hash. The special package stash (e.g. %MyClass::) counts as hash. Arrays and hashes are only shallow const, only the structure is protected, not the values. For deep constness you have to manually const all values also, or use a module.

Currently most const assignment violations are caught at compile-time, and if not you get at least an error at run-time.

Additionally to lexical variables we can also declare packages as const. That means that the structure of previously parsed package const stash can not me modified, shallow constness. You may not change, add or delete keys of the stash, but you may change the value of stash entries.

    const package MyBase { ... }
    our const %MyBase:: = {}

Especially useful are declarations of const packages and the @ISA inheritance tree to optimize method calls at compile-time.

Compile-time type checks

Assignment to const variables are only allowed once during declaration with assignment.

    my const $i = 1;
    my const ($x,$y) = (0,1);
    my const @a = (0,1);
    my const %h = ('ok' => 1, 'nok' => 0);

Declaration of a const variable without initialization XXX 1. is a compile-time error (preferred) 2. is a compile-time warning 3. silently stores undef

As Perl itself supports no types, external modules such as coretypes, types, typesafety or MooseX::Types implement checks for their types during execution of "CHECK" in perlmod blocks, at quasi compile-time.

Compile-time type optimizations

Since Perl core does not deal with types stored in comppad_name per se, type checks and optimizations are deferred to the modules which implement respective types.

The only type optimization currently in effect is constant folding, and the change of compile-time static method calls, determined either by name or by type and const-ness of all searched packages to static function calls. Thus the dynamic method search, in which object this method is implemented is avoided. This is about ~10% faster.

Constant folding

Right-hand-side expressions which resolve at compile-time to constant integers may be optimized to a CONST value, and left-hand-side numeric ops may be optimized to use their optimized <i_> counterparts. Note that i_ ops do not overflow, the integer values just wrap around. So the type and data range must be determined in advance and if not possible i_opt promotion it is forbidden.


    use coretypes;
    my int $a;

    { use integer;
      my $a = 1;

    { use integer;

    my const $a = 1;

Static method calls

    => strict::import()

When the method is defined directly in the package, it is not possible to inject another package at run-time into the method search, thus the method call can be short-cut.

const packages

    const package MyBase 0.01 {
      our @ISA = ();
      sub new { bless { @_ }, shift }
    const package MyChild 0.01 {
      our const @ISA = ('MyBase');

    my $obj = MyChild->new;
    => MyClass::new()



Types and const inheritance

    package MyBase 0.01 {
      our @ISA = ();
      sub new { bless { @_ }, shift }
    package MyChild 0.01 {
      our @ISA = ('MyBase');

    # closed call.
    my MyChild $obj = MyChild->new;
    => MyBase::new()


    package MyBase 0.01 {
      our @ISA = ();
      sub new { bless { @_ }, shift }
    const package MyChild 0.01 {
      our const @ISA = ('MyBase');

    # open call. MyChild is of type MyBase
    my MyBase $obj = MyChild->new;
    => MyBase::new()


Lexical subs NYI

Lexically defined subs are private subs but public callable and optimizable methods

    package MyClass 0.01 {
      our @ISA = ();
      my sub new { bless { @_ }, shift }
      my $private; # pad in maincv
      our $open;   # in stash

    package main;
                           # Indirect method call syntax helps.

    my $obj = MyClass::new(); # invalid
    => Undefined subroutine &MyClass::new called

Since &MyClass::new is lexically defined in the package scope, the compiler may statically optimize all method calls to &MyClass::new to an improved entersub (the CV being on a pad) without namespace lookup and dynamic method resolution, without having to const %MyClass:: and const @MyClass::ISA.



The coretypes module implements efficient implementations of natively typed scalars, arrays and hashes (at least since 5.18), and the @ISA of the three coretypes are guaranteed to be empty. Thus there will no mother of all, such as a generic type object to override coretypes, but there will be softer children of coretypes to allow stringification and undef.


See also "coretypes" in perldata for examples.

External type modules

External modules, such as types, typesafety or Moose, implement their type optimizations for the types they declare or allow declaration for during execution of "CHECK" in perlsub blocks.

XXX __PACKAGE__ types questionable


    package MyClass;
    my __PACKAGE__ $obj = __PACKAGE__->new;

Currently only the right-hand side is valid Perl.



See "Constant and typed lexical variables" in perldata for the syntax of Perl's built-in type declarations for variables, and "??? p5-mop design" for the syntax of Perl's argument and return type declarations. Strong Typing Doesn't Have to Suck

Something went wrong with that request. Please try again.