X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=blobdiff_plain;f=lib%2FDX%2FScope.pm;h=c18022a5a2015032b99b1621428f5eb1579647ad;hb=91543b6231e8bf4af4ce781efa2056b299a843e9;hp=979efb8114695ebdc74fc414e3db0791fa18f3d6;hpb=9d759b646ac5953926ce9414388c1691b8a4278b;p=scpubgit%2FDX.git diff --git a/lib/DX/Scope.pm b/lib/DX/Scope.pm index 979efb8..c18022a 100644 --- a/lib/DX/Scope.pm +++ b/lib/DX/Scope.pm @@ -1,14 +1,17 @@ package DX::Scope; +use Types::Standard qw(HashRef ArrayRef); use DX::Class; -has predicates => (is => 'ro', required => 1); +has predicates => (is => 'ro', isa => HashRef[Predicate], required => 1); -has globals => (is => 'ro', required => 1); +has globals => (is => 'ro', isa => DictValue, required => 1); -has locals => (is => 'ro', required => 1); +has locals => (is => 'ro', isa => ArrayRef[DictValue], required => 1); -has known_facts => (is => 'ro', required => 1); +has lex_map => (is => 'ro', isa => HashRef, required => 1); + +#has known_facts => (is => 'ro', required => 1); sub lookup_predicate { my ($self, $predicate) = @_; @@ -16,9 +19,16 @@ sub lookup_predicate { } sub lookup { - my ($self, $name) = @_; - my $lookup_in = ($name =~ /^[_A-Z]/ ? $self->locals->[-1] : $self->globals); - return $lookup_in->get_member_at($name) || die "No such name in scope: $name"; + my ($self, $symbol) = @_; + if ($symbol =~ /^[_A-Z]/) { + my @mapped = @{$self->lex_map->{$symbol}||[]} + or die "No such name in scope: $symbol"; + my $targ = $self; + $targ = $targ->get_member_at($_) for @mapped; + return $targ; + } + return $self->globals->get_member_at($symbol) + || die "No such name in scope: $symbol"; } sub depth { $#{$_[0]->locals} } @@ -40,7 +50,7 @@ sub with_member_at { my ($self, $at, $value) = @_; if ($at =~ /^[0-9]+$/) { my @locals = @{$self->locals}; - $locals[$at] = $at; + $locals[$at] = $value; return $self->but( locals => \@locals ); @@ -50,4 +60,12 @@ sub with_member_at { ); } +sub apply_updates { + my ($self, @updates) = @_; + my @events; + my $scope = $self; + ($scope, @events) = ($_->apply_to($scope), @events) for @updates; + return ($scope, @events); +} + 1;