File Coverage

blib/lib/Graph/AdjacencyMap/Light.pm
Criterion Covered Total %
statement 121 121 100.0
branch 56 66 84.8
condition 12 16 75.0
subroutine 25 25 100.0
pod 10 10 100.0
total 224 238 94.1


line stmt bran cond sub pod time code
1             package Graph::AdjacencyMap::Light;
2              
3             # THIS IS INTERNAL IMPLEMENTATION ONLY, NOT TO BE USED DIRECTLY.
4             # THE INTERFACE IS HARD TO USE AND GOING TO STAY THAT WAY AND
5             # ALMOST GUARANTEED TO CHANGE OR GO AWAY IN FUTURE RELEASES.
6              
7 82     82   1266 use strict;
  82         173  
  82         4081  
8 82     82   687 use warnings;
  82         326  
  82         7168  
9              
10 82     82   573 use Graph::AdjacencyMap qw(:flags :fields);
  82         179  
  82         21831  
11 82     82   677 use base 'Graph::AdjacencyMap';
  82         216  
  82         55718  
12              
13             # $SIG{__DIE__ } = \&Graph::__carp_confess;
14             # $SIG{__WARN__} = \&Graph::__carp_confess;
15              
16             my @LOCAL_OVERRIDE = (_s, _p);
17              
18             sub _is_COUNT () { 0 }
19             sub _is_MULTI () { 0 }
20             sub _is_REF () { 0 }
21              
22             sub _new {
23 4345     4345   239194 my ($class, $flags, $arity) = @_;
24 4345         17200 (my $m = $class->SUPER::_new($flags | _LIGHT, $arity))->[ _attr ] = {};
25 4345 100       22939 @$m[ @LOCAL_OVERRIDE ] = map $m->[ $_ ] ? [] : undef, @LOCAL_OVERRIDE;
26 4345         15336 $m;
27             }
28              
29             sub set_paths {
30 55568     55568 1 112623 my ($m, @paths) = @_;
31 55568         141915 my ($f, $a, $i, $pi, $map_s, $map_p, @ids) = (@$m[ _f, _arity, _i, _pi, _s, _p ]);
32 55568         105391 for (@paths) {
33 82271         129297 my $k = $_;
34 82271 50 66     259370 Graph::__carp_confess("Wrong number of args, want $a, got (@$k)") if $a != 1 and $a != @$k;
35 82271 100       239738 my $l = $a == 1 ? $k : join ' ', @$k;
36 82271 100       206148 push(@ids, $pi->{ $l }), next if defined $pi->{ $l };
37 70323         179889 $i->[ my $n = $m->[ _n ]++ ] = $_;
38 70323         176775 $pi->{ $l } = $n;
39 70323         116252 push @ids, $n;
40 70323 100       179049 _successors_add($f, $map_s, $map_p, $n, $_) if $map_s;
41             }
42 55568         140202 @ids;
43             }
44              
45             sub _successors_set {
46 52579     52579   81245 my $val = pop;
47 52579         105396 my ($f, $map_s, $map_p, $id, $path) = @_;
48 52579         139498 my $pairs = Graph::AdjacencyMap::_successors_cartesian(($f & _UNORD), 0, $path);
49 82     82   703 no warnings 'uninitialized'; # needed 5.8
  82         171  
  82         160407  
50 52579         299809 vec($map_s->[ $_->[0] ], $_->[1], 1) = $val for @$pairs; # row-major
51 52579 100       192807 return if !$map_p;
52 15573         58895 vec($map_p->[ $_->[1] ], $_->[0], 1) = $val for @$pairs;
53             }
54 52049     52049   104729 sub _successors_add { push @_, 1; goto &_successors_set }
  52049         125802  
55 530     530   1256 sub _successors_del { push @_, 0; goto &_successors_set }
  530         1633  
56              
57             sub _paths_fromto {
58 1993     1993   3362 my $offset = pop;
59 1993         3735 my ($i, $pi, $f, $map_x, @v) = ( @{ $_[0] }[ _i, _pi, _f, $offset ], @_[1..$#_] );
  1993         8094  
60 1993 50       7268 Graph::__carp_confess("undefined vertex") if grep !defined, @v;
61 1993         13234 require Set::Object;
62 1993         38848 my ($paths, $invert, $unord) = (Set::Object->new, $offset == _p, $f & _UNORD);
63 1993         17421 for my $tuple (grep defined $_->[1], map [$_, $map_x->[$_]], @v) {
64 9816         28474 my ($v, $s) = ($tuple->[0], scalar unpack("b*", $tuple->[1]));
65 9816 100       120611 $paths->insert(join ' ', (
    100          
66             $unord ? sort($v, pos($s) - 1) :
67             $invert ? (pos($s) - 1, $v) : ($v, pos($s) - 1)
68             )) while $s =~ /1/g;
69             }
70 1993         40834 map $i->[ $pi->{ $_ } ], $paths->members;
71             }
72 1664     1664 1 4994 sub paths_from { push @_, _s; goto &_paths_fromto }
  1664         5691  
73 329     329 1 1407 sub paths_to { push @_, _p; goto &_paths_fromto }
  329         726  
74              
75             sub _cessors {
76 37261     37261   57798 my $offset = pop;
77 37261         54396 my ($map_x, @v) = ( @{ $_[0] }[ $offset ], @_[1..$#_] );
  37261         129189  
78 37261 50       101630 Graph::__carp_confess("undefined vertex") if grep !defined, @v;
79 37261         185809 require Set::Object;
80 37261         277819 my $c = Set::Object->new;
81 37261         103665 for my $row (grep defined, @$map_x[ @v ]) {
82             # 10x quicker than: grep vec($row, $_, 1), 0..$#$m
83 36487         95011 my $s = unpack("b*", $row);
84 36487         558751 $c->insert(pos($s) - 1) while $s =~ /1/g;
85             }
86 37261         291515 $c->members;
87             }
88 35942     35942 1 66551 sub successors { push @_, _s; goto &_cessors }
  35942         122623  
89 1319     1319 1 3512 sub predecessors { push @_, _p; goto &_cessors }
  1319         3346  
90              
91             sub has_successor {
92 10     10 1 1258 my ($map_s, $u, $v) = ( @{ $_[0] }[ _s ], @_[1, 2] );
  10         30  
93 10 50       36 Graph::__carp_confess("undefined vertex") if grep !defined, $u, $v;
94 10   100     59 vec(($map_s->[ $u ] || return 0), $v, 1);
95             }
96              
97             sub get_ids_by_paths {
98 61980     61980 1 115044 my ($pi, $m, $list, $ensure, $deep) = ( @{ $_[0] }[ _pi ], @_ );
  61980         166840  
99 61980   100     177406 $deep ||= 0;
100             map {
101 61980         115299 my @ret = map {
102 87847 100       203244 my @ret2 = map {
103 146055 100       264052 my $id = $pi->{ $_ };
  146068         293988  
104 146068 100       323629 defined $id ? $id : $ensure ? $m->set_paths($_) : return;
    100          
105             } $deep > 1 ? @$_ : $_;
106 146017 100       367276 $deep > 1 ? \@ret2 : @ret2;
107             } $deep ? @$_ : $_;
108 87809 100       260359 $deep ? \@ret : @ret;
109             } @$list;
110             }
111              
112             sub has_path {
113 1017     1017 1 4907 my ($a, $pi, $k) = ( @{ $_[0] }[ _arity, _pi ], $_[1] );
  1017         2469  
114 1017 50 66     3478 Graph::__carp_confess("Wrong number of args, want $a, got (@$k)") if $a != 1 and $a != @$k;
115 1017 100       6107 $pi->{ $a == 1 ? $k : join ' ', @$k };
116             }
117              
118             sub _get_path_count {
119 882 100   882   3189 defined(my $dummy = &has_path) ? 1 : 0; # defined &x asks if func defined
120             }
121              
122             sub del_path {
123 565     565 1 3297 my ($f, $a, $i, $pi, $map_s, $map_p, $attr, $k) = ( @{ my $m = $_[0] }[ _f, _arity, _i, _pi, _s, _p, _attr ], $_[1] );
  565         2222  
124 565 50 66     3809 Graph::__carp_confess("Wrong number of args, want $a, got (@$k)") if $a != 1 and $a != @$k;
125 565 100       2177 my $l = $a == 1 ? $k : join ' ', @$k;
126 565 100       1719 return 0 if !exists $pi->{ $l };
127 558         1201 my $id = delete $pi->{ $l };
128 558         942 delete $attr->{ $l };
129 558         1167 my $path = delete $i->[ $id ];
130 558 100       2209 _successors_del($f, $map_s, $map_p, $id, $path) if $map_s;
131 558         2385 return 1;
132             }
133              
134             sub rename_path {
135 12     12 1 1009 my ($m, $from, $to) = @_;
136 12         39 my ($a, $i, $pi, $attr) = @$m[ _arity, _i, _pi, _attr ];
137 12 50       53 return 1 if $a > 1; # arity > 1, all integers, no names
138 12 50       38 return 0 unless exists $pi->{ $from };
139 12 100       32 $attr->{ $to } = delete $attr->{ $from } if $attr->{ $from };
140 12         46 $i->[ $pi->{ $to } = delete $pi->{ $from } ] = $to;
141 12         40 return 1;
142             }
143              
144             sub _set_path_attr_common {
145 5801     5801   20597 (my $m = $_[0])->set_paths($_[1]);
146 5801         14072 my ($a, $attr, $k) = ( @$m[ _arity, _attr ], $_[1] );
147 5801 100       14372 my $l = $a == 1 ? $k : join ' ', @$k;
148 5801         37852 \$attr->{ $l };
149             }
150              
151             sub _get_path_attrs {
152 12266     12266   20893 my ($a, $attr, $k) = ( @{ $_[0] }[ _arity, _attr ], $_[1] );
  12266         37481  
153 12266 50 66     50530 Graph::__carp_confess("Wrong number of args, want $a, got (@$k)") if $a != 1 and $a != @$k;
154 12266 100       41453 my $l = $a == 1 ? $k : join ' ', @$k;
155 12266         123177 $attr->{ $l };
156             }
157              
158             sub _del_path_attrs {
159 13 50   13   51 return undef unless defined &has_path;
160 13         25 my ($a, $attr, $k) = ( @{ $_[0] }[ _arity, _attr ], $_[1] );
  13         38  
161 13 100       45 my $l = $a == 1 ? $k : join ' ', @$k;
162 13 100       61 return 0 unless exists $attr->{ $l };
163 11         25 delete $attr->{ $l };
164 11         39 1;
165             }
166              
167             1;