File Coverage

blib/lib/Class/Builtin/Array.pm
Criterion Covered Total %
statement 61 171 35.6
branch 5 32 15.6
condition 0 2 0.0
subroutine 19 50 38.0
pod 1 43 2.3
total 86 298 28.8


line stmt bran cond sub pod time code
1             package Class::Builtin::Array;
2 4     4   147 use 5.008001;
  4         18  
  4         222  
3 4     4   28 use warnings;
  4         8  
  4         147  
4 4     4   28 use strict;
  4         7  
  4         373  
5             our $VERSION = sprintf "%d.%02d", q$Revision: 0.4 $ =~ /(\d+)/g;
6              
7 4     4   26 use Carp;
  4         9  
  4         439  
8 4     4   29 use List::Util ();
  4         43  
  4         138  
9              
10             use overload (
11 4         52 '""' => \&Class::Builtin::Array::dump,
12 4     4   168 );
  4         8  
13              
14             sub new{
15 13     13 0 29 my $class = shift;
16 13         22 my $aref = shift;
17 13         37 bless [ map { Class::Builtin->new($_) } @$aref ], $class;
  66         201  
18             }
19              
20             sub clone{
21 0     0 0 0 __PACKAGE__->new([ @{$_[0]} ]);
  0         0  
22             }
23              
24 0     0 0 0 sub get { $_[0]->[ $_[1] ] }
25              
26 0     0 0 0 sub set { $_[0]->[ $_[1] ] = Class::Builtin->new( $_[2] ) }
27              
28             sub unbless {
29 12     12 0 19 my $self = shift;
30             [
31 12 50       386 CORE::map { eval { $_->can('unbless') } ? $_->unbless : $_ } @$self
  84         103  
  84         474  
32             ];
33             }
34              
35             sub dump {
36 12     12 0 5983 local ($Data::Dumper::Terse) = 1;
37 12         19 local ($Data::Dumper::Indent) = 0;
38 12         21 local ($Data::Dumper::Useqq) = 1;
39 12         33 sprintf 'OO(%s)', Data::Dumper::Dumper($_[0]->unbless);
40             }
41              
42              
43             for my $unary (qw/shift pop/) {
44 4     4 0 8 eval qq{
  4     1 0 15  
  1         726  
  1         6  
45             sub Class::Builtin::Array::$unary
46             { CORE::$unary \@{\$_[0]} }
47             };
48             croak $@ if $@;
49             }
50              
51             for my $binary (qw/unshift push/) {
52 2     2 0 4 eval qq{
  2     1 0 5  
  2         8  
  2         6  
  1         4  
  1         4  
  1         7  
  1         6  
53             sub Class::Builtin::Array::$binary
54             {
55             my \$self = CORE::shift;
56             CORE::$binary \@\$self, map { Class::Builtin->new(\$_) } \@_;
57             \$self;
58             }
59             };
60             croak $@ if $@;
61             }
62              
63             sub reverse {
64 1     1 0 4 __PACKAGE__->new( [ reverse @{ $_[0] } ] );
  1         12  
65             }
66              
67             sub splice {
68 2     2 0 9 my $self = CORE::shift;
69 2         9 my @ret =
70             @_ == 0 ? CORE::splice @$self
71             : @_ == 1 ? CORE::splice @$self, $_[0]
72             : @_ == 2 ? CORE::splice @$self, $_[0], $_[1]
73             : CORE::splice @$self, $_[0], $_[1],
74 2 100       28 map { Class::Builtin->new($_) } CORE::splice @_, 2;
    50          
    50          
75 2         15 __PACKAGE__->new( [@ret] );
76             }
77              
78             sub spliced{
79 0     0 0 0 my $clone = CORE::shift->clone;
80 0         0 $clone->splice(@_);
81 0         0 $clone;
82             }
83              
84             for my $passive (qw/shift pop unshift push/) {
85 0     0 0 0 eval qq{
  0     0 0 0  
  0     0 0 0  
  0     0 0 0  
  0         0  
  0         0  
  0         0  
  0         0  
86             sub Class::Builtin::Array::${passive}ed
87             {
88             my \$self = CORE::shift;
89             \$self->clone->$passive(\@_);
90             }
91             };
92             croak $@ if $@;
93             }
94              
95             sub delete {
96 0     0 0 0 my $self = shift;
97 0         0 my @deleted = CORE::delete @{$self}[@_];
  0         0  
98 0         0 Class::Builtin::Array->new([@deleted]);
99             }
100              
101             sub concat {
102 1     1 0 3 my $self = shift;
103 1         3 my $ary = shift;
104 1         3 push @$self, @$ary;
105 1         7 $self;
106             }
107              
108 0     0 0 0 sub ref { Class::Builtin::Scalar->new(CORE::ref $_[0]) }
109 4     4 0 7 sub length { Class::Builtin::Scalar->new(CORE::scalar @{$_[0]}) }
  4         21  
110              
111             sub sort {
112 0     0 0 0 my $self = CORE::shift;
113 0         0 my $block = CORE::shift;
114             my @sorted = $block
115 0 0       0 ? do {
116 0         0 my $pkg = caller; # ugly but works
117 0         0 eval qq{ package $pkg; CORE::sort(\$block \@\$self) };
118             }
119             : CORE::sort(@$self);
120 0         0 __PACKAGE__->new( [@sorted] );
121             }
122              
123             sub grep {
124 0     0 0 0 my $self = CORE::shift;
125 0 0       0 my $block = CORE::shift or croak;
126 0         0 my @grepped;
127 0 0       0 if ( CORE::ref $block eq 'Regexp' ) {
128 0         0 for (@$self) {
129 0 0       0 $_ =~ $block or next;
130 0         0 push @grepped, $_;
131             }
132             }
133             else {
134 0         0 for (@$self) {
135 0 0       0 $block->($_) or next;
136              
137             }
138             }
139 0         0 __PACKAGE__->new( [@grepped] );
140             }
141              
142             sub map {
143 0     0 0 0 my $self = CORE::shift;
144 0 0       0 my $block = CORE::shift or croak;
145 0         0 my @mapped;
146 0         0 CORE::push @mapped, $block->($_) for (@$self);
147 0         0 __PACKAGE__->new([ @mapped ]);
148             }
149              
150             *each = \↦
151              
152             sub each_with_index {
153 0     0 0 0 my $self = CORE::shift;
154 0 0       0 my $block = CORE::shift or croak;
155 0         0 my @mapped;
156 0         0 for my $i ( 0 .. $self->length - 1 ) {
157 0         0 CORE::push @mapped,
158             $block->( $self->[$i], Class::Builtin::Scalar->new($i) );
159             }
160 0         0 __PACKAGE__->new( [@mapped] );
161             }
162              
163             sub join {
164 0     0 0 0 my $self = CORE::shift;
165 0   0     0 my $sep = CORE::shift || '';
166 0         0 my $str = CORE::join( $sep, @$self );
167 0         0 Class::Builtin::Scalar->new($str);
168             }
169              
170             sub pack {
171 1     1 0 3 my $self = CORE::shift;
172 1         2 my $form = CORE::shift;
173 1         10 my $str = CORE::pack( $form, @$self );
174 1         6 Class::Builtin::Scalar->new($str);
175             }
176              
177             sub print {
178 0     0 0   my $self = shift;
179 0 0         @_ ? CORE::print {$_[0]} @$self : CORE::print @$self;
  0            
180             }
181              
182             sub say {
183 0     0 0   my $self = shift;
184 0           local $\ = "\n";
185 0           local $, = ",";
186 0 0         @_ ? CORE::print {$_[0]} @$self : CORE::print @$self;
  0            
187             }
188              
189             sub methods {
190 0           Class::Builtin::Array->new(
191 0     0 1   [ sort grep { defined &{$_} } keys %Class::Builtin::Array:: ] );
  0            
192             }
193              
194             # List::Util related
195              
196             for my $meth (qw(max maxstr min minstr sum)){
197 0     0 0   eval qq{
  0     0 0    
  0     0 0    
  0     0 0    
  0     0 0    
  0            
  0            
  0            
  0            
  0            
  0            
  0            
  0            
  0            
  0            
198             sub Class::Builtin::Array::$meth
199             {
200             my \$ret = List::Util::$meth(\@{\$_[0]});
201             Class::Builtin::Scalar->new(\$ret);
202             }
203             };
204             croak $@ if $@;
205             }
206              
207             # They are reinvented. Sigh;
208              
209             sub first {
210 0     0 0   my $self = CORE::shift;
211 0 0         my $block = CORE::shift or croak;
212 0           for (@$self){
213 0 0         return $_ if $block->($_);
214             }
215 0           return;
216             }
217              
218             sub reduce {
219 0     0 0   my $self = CORE::shift;
220 0 0         my $block = CORE::shift or croak;
221 0           my $reduced = $self->[0];
222 0           my $pkg = caller;
223 0           for ( @$self[ 1 .. $self->length - 1 ] ) {
224 4     4   14827 no strict 'refs';
  4         17  
  4         1241  
225 0           ${ $pkg . '::a' } = $reduced;
  0            
226 0           ${ $pkg . '::b' } = $_;
  0            
227 0           $reduced = $block->();
228             }
229 0           return Class::Builtin::Scalar->new($reduced);
230             }
231              
232             sub shuffle {
233 0     0 0   __PACKAGE__->new( [ List::Util::shuffle @{ $_[0] } ] );
  0            
234             }
235              
236             # Scalar::Util related
237             for my $meth (qw/blessed isweak refaddr reftype weaken/){
238 0     0 0   eval qq{
  0     0 0    
  0     0 0    
  0     0 0    
  0     0 0    
  0            
  0            
  0            
  0            
  0            
  0            
  0            
  0            
  0            
  0            
239             sub Class::Builtin::Array::$meth
240             {
241             my \$self = CORE::shift;
242             my \$ret = Scalar::Util::$meth(\$self);
243             __PACKAGE__->new(\$ret);
244             }
245             };
246             croak $@ if $@;
247             }
248              
249             1; # end of Class::Builtin::Array
250              
251             =head1 NAME
252              
253             Class::Builtin::Array - Array as an object
254              
255             =head1 VERSION
256              
257             $Id: Array.pm,v 0.4 2011/05/21 21:40:54 dankogai Exp dankogai $
258              
259             =head1 SYNOPSIS
260              
261             use Class::Builtin::Array; # use Class::Builtin;
262             my $foo = Class::Builtin::Array->new([0..9]); # OO([0..9]);
263             print $foo->length; # 10
264              
265             =head1 EXPORT
266              
267             None. But see L
268              
269             =head1 METHODS
270              
271             This section is under construction. For the time being, try
272              
273             print Class::Builtin::Array->new([])->methods->join("\n")
274              
275             =head1 TODO
276              
277             This section itself is to do :)
278              
279             =over 2
280              
281             =item * more methods
282              
283             =back
284              
285             =head1 SEE ALSO
286              
287             L, L, L L
288              
289             =head1 AUTHOR
290              
291             Dan Kogai, C<< >>
292              
293             =head1 ACKNOWLEDGEMENTS
294              
295             L, L, L
296              
297             =head1 COPYRIGHT & LICENSE
298              
299             Copyright 2009 Dan Kogai, all rights reserved.
300              
301             This program is free software; you can redistribute it and/or modify it
302             under the same terms as Perl itself.
303              
304             =cut