File Coverage

blib/lib/Data/Munge.pm
Criterion Covered Total %
statement 69 69 100.0
branch 28 36 77.7
condition 9 9 100.0
subroutine 18 18 100.0
pod 10 10 100.0
total 134 142 94.3


line stmt bran cond sub pod time code
1             package Data::Munge;
2 3     3   681885 use strict;
  3         19  
  3         86  
3 3     3   16 use warnings;
  3         5  
  3         92  
4 3     3   15 use Exporter 5.57 qw(import);
  3         75  
  3         3223  
5              
6 8     8   468 sub _eval { eval $_[0] } # empty lexical scope
7              
8             our $VERSION = '0.10';
9             our @EXPORT = qw(
10             byval
11             elem
12             eval_string
13             list2re
14             mapval
15             rec
16             replace
17             slurp
18             submatches
19             trim
20             );
21              
22             sub byval (&$) {
23 1     1 1 6251 my ($f, $x) = @_;
24 1         3 local *_ = \$x;
25 1         5 $f->($_);
26 1         9 $x
27             }
28              
29             sub elem {
30 37     37 1 960 my ($k, $xs) = @_;
31 37 100       86 if (ref $k) {
    100          
32 28         46 for my $x (@$xs) {
33 43 100 100     151 return 1 if ref $x && $k == $x;
34             }
35             } elsif (defined $k) {
36 8         16 for my $x (@$xs) {
37 15 100 100     73 return 1 if defined $x && !ref $x && $k eq $x;
      100        
38             }
39             } else {
40 1         4 for my $x (@$xs) {
41 1 50       6 return 1 if !defined $x;
42             }
43             }
44 18         59 !1
45             }
46              
47             sub eval_string {
48 8     8 1 7701 my ($code) = @_;
49 8         31 my ($package, $file, $line) = caller;
50 8         18 local $Data::Munge::_err = $@;
51 8         30 $code = qq{\$\@ = \$Data::Munge::_err; package $package; # eval_string()\n#line $line "$file"\n$code};
52 8 50       28 my @r = wantarray ? _eval $code : scalar _eval $code;
53 8 100       93 die $@ if $@;
54 5         13 $@ = $Data::Munge::_err;
55 5 50       34 wantarray ? @r : $r[0]
56             }
57              
58             sub list2re {
59 5 100   5 1 194 @_ or return qr/(?!)/;
60 4 50       18 my $re = join '|', map quotemeta, sort {length $b <=> length $a || $a cmp $b } @_;
  20         52  
61 4 100       15 $re eq '' and $re = '(?#)';
62 4         118 qr/$re/
63             }
64              
65             sub mapval (&@) {
66 1     1 1 3 my $f = shift;
67 1         4 my @xs = @_;
68 1         3 map { $f->($_); $_ } @xs
  3         8  
  3         25  
69             }
70              
71             if ($^V ge v5.16.0) {
72 3     3   28 eval_string <<'EOT';
  3         18  
73             use v5.16;
74 1     1 1 3 sub rec (&) {
75 11     11   494 my ($f) = @_;
76 1         4 sub { $f->(__SUB__, @_) }
77             }
78             EOT
79             } elsif (eval { require Scalar::Util } && defined &Scalar::Util::weaken) {
80             *rec = sub (&) {
81             my ($f) = @_;
82             my $w;
83             my $r = $w = sub { $f->($w, @_) };
84             Scalar::Util::weaken($w);
85             $r
86             };
87             } else {
88             # slow but always works
89             *rec = sub (&) {
90             my ($f) = @_;
91             sub { $f->(&rec($f), @_) }
92             };
93             }
94              
95             sub replace {
96 7     7 1 56 my ($str, $re, $x, $g) = @_;
97             my $f = ref $x ? $x : sub {
98 28     28   43 my $r = $x;
99 28         48 $r =~ s{\$([\$&`'0-9]|\{([0-9]+)\})}{
100 2 50       18 $+ eq '$' ? '$' :
    50          
    50          
    50          
101             $+ eq '&' ? $_[0] :
102             $+ eq '`' ? substr($_[-1], 0, $_[-2]) :
103             $+ eq "'" ? substr($_[-1], $_[-2] + length $_[0]) :
104             $_[$+]
105             }eg;
106 28         78 $r
107 7 100       43 };
108 7 100       24 if ($g) {
109 6         40 $str =~ s{$re}{ $f->(substr($str, $-[0], $+[0] - $-[0]), submatches(), $-[0], $str) }eg;
  30         155  
110             } else {
111 1         8 $str =~ s{$re}{ $f->(substr($str, $-[0], $+[0] - $-[0]), submatches(), $-[0], $str) }e;
  1         7  
112             }
113 7         64 $str
114             }
115              
116             sub slurp {
117 1     1 1 238 local $/;
118 1         30 scalar readline $_[0]
119             }
120              
121             sub submatches {
122 3     3   24 no strict 'refs';
  3         5  
  3         450  
123 33     33 1 131 map $$_, 1 .. $#+
124             }
125              
126             sub trim {
127 9     9 1 19 my ($s) = @_;
128 9 100       21 return undef if !defined $s;
129 8         31 $s =~ s/^\s+//;
130 8         22 $s =~ s/\s+\z//;
131 8         38 $s
132             }
133              
134             'ok'
135              
136             __END__