line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package Blessed::Merge; |
2
|
|
|
|
|
|
|
|
3
|
5
|
|
|
5
|
|
596255
|
use 5.006; |
|
5
|
|
|
|
|
64
|
|
4
|
|
|
|
|
|
|
|
5
|
|
|
|
|
|
|
our $VERSION = '0.11'; |
6
|
5
|
|
|
5
|
|
32
|
use strict; |
|
5
|
|
|
|
|
9
|
|
|
5
|
|
|
|
|
119
|
|
7
|
5
|
|
|
5
|
|
23
|
use warnings; |
|
5
|
|
|
|
|
12
|
|
|
5
|
|
|
|
|
189
|
|
8
|
5
|
|
|
5
|
|
27
|
use Scalar::Util qw/reftype/; |
|
5
|
|
|
|
|
10
|
|
|
5
|
|
|
|
|
283
|
|
9
|
5
|
|
|
5
|
|
32
|
use Carp qw/croak/; |
|
5
|
|
|
|
|
8
|
|
|
5
|
|
|
|
|
265
|
|
10
|
5
|
|
|
5
|
|
2271
|
use Combine::Keys qw/combine_keys/; |
|
5
|
|
|
|
|
92426
|
|
|
5
|
|
|
|
|
45
|
|
11
|
5
|
|
|
5
|
|
2927
|
use Tie::IxHash; |
|
5
|
|
|
|
|
20938
|
|
|
5
|
|
|
|
|
4769
|
|
12
|
|
|
|
|
|
|
|
13
|
|
|
|
|
|
|
sub new { |
14
|
6
|
100
|
100
|
6
|
1
|
4327
|
my ($pkg, $args) = (shift, reftype $_[0] || "" eq 'HASH' ? $_[0] : {@_}); |
15
|
6
|
|
|
|
|
19
|
my $self = bless $args, $pkg; |
16
|
6
|
|
100
|
|
|
64
|
$self->{$_} = $self->{$_} // 1 foreach (qw/same blessed/); |
17
|
6
|
|
100
|
|
|
47
|
$self->{$_} = $self->{$_} // 0 foreach(qw/unique_array unique_hash/); |
18
|
6
|
|
|
|
|
59
|
$self->{itterator} = 1; |
19
|
6
|
|
|
|
|
23
|
return $self; |
20
|
|
|
|
|
|
|
} |
21
|
|
|
|
|
|
|
|
22
|
|
|
|
|
|
|
sub merge { |
23
|
10
|
|
|
10
|
1
|
10343
|
my ($self, $base_bless, $new) = (shift, ref $_[0], shift); |
24
|
10
|
|
|
|
|
51
|
tie my %isa, 'Tie::IxHash'; |
25
|
10
|
|
|
|
|
202
|
$isa{$base_bless} = $new; |
26
|
|
|
|
|
|
|
map { |
27
|
10
|
100
|
|
|
|
191
|
if ( $self->{same} ) { |
|
15
|
|
|
|
|
60
|
|
28
|
9
|
100
|
|
|
|
197
|
croak 'Attempting to merge two different *packages*' unless $base_bless eq ref $_; |
29
|
|
|
|
|
|
|
} else { |
30
|
6
|
|
|
|
|
12
|
my $r = ref $_; |
31
|
6
|
50
|
|
|
|
37
|
$isa{$r} = $_ unless $r =~ m/HASH|ARRAY|SCALAR/; |
32
|
|
|
|
|
|
|
} |
33
|
14
|
|
|
|
|
120
|
$new = $self->_merge($new, $_); |
34
|
|
|
|
|
|
|
} @_; |
35
|
9
|
|
|
|
|
53
|
for my $f (keys %isa) { |
36
|
14
|
50
|
|
|
|
394
|
my $check = $isa{$f} or next; |
37
|
14
|
|
100
|
|
|
161
|
$_ eq $f and next or $check->isa($_) and delete $isa{$_} for keys %isa; |
|
|
|
66
|
|
|
|
|
|
|
|
33
|
|
|
|
|
38
|
|
|
|
|
|
|
} |
39
|
9
|
100
|
|
|
|
249
|
return $self->{blessed} ? scalar keys %isa == 1 ? bless $new, $base_bless : do { |
|
|
100
|
|
|
|
|
|
40
|
2
|
|
|
|
|
42
|
my $class = sprintf "Blessed::Merge::__ANON__::%s", $self->{itterator}++; |
41
|
2
|
|
|
|
|
7
|
eval sprintf('package %s; our @ISA = qw/%s/; 1;', $class, join ' ', keys %isa); |
42
|
2
|
|
|
|
|
23
|
return bless $new, $class; |
43
|
|
|
|
|
|
|
} : $new; |
44
|
|
|
|
|
|
|
} |
45
|
|
|
|
|
|
|
|
46
|
|
|
|
|
|
|
sub _merge { |
47
|
74
|
|
|
74
|
|
317
|
my ($self, $new, $merger) = @_; |
48
|
74
|
100
|
|
|
|
171
|
return $new unless defined $merger; |
49
|
66
|
|
100
|
|
|
178
|
my $new_ref = reftype($new) || ''; |
50
|
66
|
|
100
|
|
|
155
|
my $merger_ref = reftype($merger) || 'SCALAR'; |
51
|
|
|
|
|
|
|
$merger_ref eq 'HASH' ? do { |
52
|
36
|
100
|
|
|
|
72
|
$new = {} if ( $new_ref ne 'HASH' ); |
53
|
|
|
|
|
|
|
return { |
54
|
|
|
|
|
|
|
$self->{unique_hash} |
55
|
|
|
|
|
|
|
? $self->_unique_merge($merger_ref, $new, $merger) |
56
|
36
|
100
|
|
|
|
109
|
: map +( $_ => $self->_merge( $new->{$_}, $merger->{$_} ) ), combine_keys($new, $merger) |
57
|
|
|
|
|
|
|
}; |
58
|
66
|
100
|
|
|
|
191
|
} : $merger_ref eq 'ARRAY' ? do { |
|
|
100
|
|
|
|
|
|
59
|
|
|
|
|
|
|
$new_ref eq 'ARRAY' ? do { |
60
|
11
|
100
|
|
11
|
|
15
|
my $length = sub {$_[0] < $_[1] ? $_[1] : $_[0]}->(scalar @{$new}, scalar @{$merger}); |
|
11
|
|
|
|
|
25
|
|
|
11
|
|
|
|
|
18
|
|
|
11
|
|
|
|
|
42
|
|
61
|
|
|
|
|
|
|
[ $self->{unique_array} |
62
|
|
|
|
|
|
|
? $self->_unique_merge($merger_ref, $new, $merger, $length) |
63
|
11
|
100
|
|
|
|
64
|
: map { $self->_merge($new->[$_], $merger->[$_]) } 0 .. $length - 1 |
|
6
|
|
|
|
|
14
|
|
64
|
|
|
|
|
|
|
]; |
65
|
13
|
100
|
|
|
|
26
|
} : [ map { $self->_merge('', $_ ) } @{ $merger } ]; # destroy da references |
|
6
|
|
|
|
|
20
|
|
|
2
|
|
|
|
|
5
|
|
66
|
|
|
|
|
|
|
} : $merger; |
67
|
|
|
|
|
|
|
} |
68
|
|
|
|
|
|
|
|
69
|
|
|
|
|
|
|
sub _unique_merge { |
70
|
28
|
|
|
28
|
|
58
|
my ($s, $r, $n, $m, $l) = @_; |
71
|
28
|
100
|
|
|
|
51
|
($r eq 'ARRAY') && do { |
72
|
9
|
|
|
|
|
14
|
my (@z, %u, $x1, $x2); |
73
|
9
|
|
|
|
|
19
|
for (my $i = 0; $i < $l; $i++) { |
74
|
|
|
|
|
|
|
my $c = grep { |
75
|
24
|
|
|
|
|
41
|
my ($x) = reftype(\$_); |
|
48
|
|
|
|
|
82
|
|
76
|
48
|
100
|
100
|
|
|
151
|
$x eq 'SCALAR' ? !$_ || exists $u{$_} ? 1 : do { $u{$_} = 1; push @z, $_; } : 0; |
|
27
|
100
|
|
|
|
49
|
|
|
27
|
|
|
|
|
52
|
|
77
|
|
|
|
|
|
|
} ($n->[$i], $m->[$i]); |
78
|
24
|
100
|
|
|
|
53
|
do { ($x1, $x2) = (reftype($n->[$i]), reftype($m->[$i])); $c == 0 } |
|
5
|
100
|
|
|
|
16
|
|
|
5
|
100
|
|
|
|
25
|
|
|
|
100
|
|
|
|
|
|
79
|
|
|
|
|
|
|
? $x1 eq $x2 |
80
|
|
|
|
|
|
|
? push @z, $s->_merge($n->[$i], $m->[$i]) |
81
|
|
|
|
|
|
|
: push @z, $n->[$i], $m->[$i] |
82
|
|
|
|
|
|
|
: $x1 |
83
|
|
|
|
|
|
|
? push @z, $n->[$i] |
84
|
|
|
|
|
|
|
: push @z, $m->[$i] if $c != 2; |
85
|
|
|
|
|
|
|
} |
86
|
9
|
|
|
|
|
48
|
return @z; |
87
|
|
|
|
|
|
|
}; |
88
|
19
|
|
|
|
|
25
|
my %z = %{ $n }; |
|
19
|
|
|
|
|
69
|
|
89
|
|
|
|
|
|
|
map { |
90
|
31
|
|
100
|
|
|
87
|
my $x = reftype($m->{$_}) || 'SCALAR'; |
91
|
|
|
|
|
|
|
exists $z{$_} ? $x ne 'SCALAR' && $x eq reftype($z{$_}) |
92
|
31
|
100
|
100
|
|
|
121
|
? do { $z{$_} = $s->_merge($z{$_}, $m->{$_}) } : '*\o/*' : do { $z{$_} = $m->{$_} } |
|
21
|
100
|
|
|
|
47
|
|
|
4
|
|
|
|
|
10
|
|
93
|
19
|
|
|
|
|
33
|
} keys %{ $m }; |
|
19
|
|
|
|
|
39
|
|
94
|
19
|
|
|
|
|
88
|
return %z; |
95
|
|
|
|
|
|
|
} |
96
|
|
|
|
|
|
|
|
97
|
|
|
|
|
|
|
1; |
98
|
|
|
|
|
|
|
|
99
|
|
|
|
|
|
|
__END__ |