Sorry for the Java jargon, but how can I overload Moose constructors?
Suppose I'm representing a segment. I can either take a start point and and point, or a start point and length, or end point and length.
How can I allow for such alternative construction methods?
You don't need to override new
. You can supply your own BUILD
:
#!/usr/bin/perl
package My::Segment;
use Moose;
use namespace::autoclean;
use Carp qw( confess );
has 'start' => (is => 'ro', isa => 'Num',
predicate => 'has_start', writer => '_set_start',
);
has 'end' => (is => 'ro', isa => 'Num',
predicate => 'has_end', writer => '_set_end',
);
has 'length' => (is => 'ro', isa => 'Num',
predicate => 'has_length', writer => '_set_length',
);
sub BUILD {
my $self = shift;
$self->has_start and $self->has_end and $self->length and do {
return if $self->length == $self->end - $self->start;
confess "Inconsistent start, end and length";
};
$self->has_start and $self->has_end and do {
$self->_set_length($self->end - $self->start);
return;
};
$self->has_start and $self->has_length and do {
$self->_set_end($self->start + $self->length);
return;
};
$self->has_end and $self->has_length and do {
$self->_set_start($self->end - $self->length);
return;
};
confess "At least two of start, end or length must be supplied";
}
__PACKAGE__->meta->make_immutable;
package main;
use YAML;
my $x = My::Segment->new(start => 0, length => 3);
my $y = My::Segment->new(start => 1, end => 4);
my $z = My::Segment->new(end => 5, length => 3);
print Dump($_) for $x, $y, $z;
my $w = My::Segment->new(start => 0, end => 0, length => 1);