File Coverage

blib/lib/Perl/Critic/Policy/Freenode/Each.pm
Criterion Covered Total %
statement 24 25 96.0
branch 2 2 100.0
condition 2 3 66.6
subroutine 10 11 90.9
pod 4 5 80.0
total 42 46 91.3


line stmt bran cond sub pod time code
1             package Perl::Critic::Policy::Freenode::Each;
2              
3 1     1   536 use strict;
  1         3  
  1         23  
4 1     1   4 use warnings;
  1         1  
  1         23  
5              
6 1     1   4 use Perl::Critic::Utils qw(:severities :classification :ppi);
  1         2  
  1         39  
7 1     1   291 use parent 'Perl::Critic::Policy';
  1         2  
  1         6  
8              
9             our $VERSION = '0.032';
10              
11 1     1   58 use constant DESC => 'each() called';
  1         2  
  1         54  
12 1     1   6 use constant EXPL => 'The each function may cause undefined behavior when operating on the hash while iterating. Use a foreach loop over the hash\'s keys or values instead.';
  1         2  
  1         134  
13              
14 2     2 0 6602 sub supported_parameters { () }
15 1     1 1 15 sub default_severity { $SEVERITY_LOW }
16 0     0 1 0 sub default_themes { 'freenode' }
17 2     2 1 15089 sub applies_to { 'PPI::Token::Word' }
18              
19             sub violates {
20 5     5 1 94 my ($self, $elem) = @_;
21 5 100 66     12 return () unless $elem eq 'each' and is_function_call $elem;
22 1         388 return $self->violation(DESC, EXPL, $elem);
23             }
24              
25             1;
26              
27             =head1 NAME
28              
29             Perl::Critic::Policy::Freenode::Each - Don't use each to iterate through a hash
30              
31             =head1 DESCRIPTION
32              
33             The C<each()> function relies on an iterator internal to a hash (or array),
34             which is the same iterator used by C<keys()> and C<values()>. So deleting or
35             adding hash elements during iteration, or just calling C<keys()> or C<values()>
36             on the hash, will cause undefined behavior and the code will likely break. This
37             could occur even by passing the hash to other functions which operate on the
38             hash. Instead, use a C<foreach> loop iterating through the keys or values of
39             the hash.
40              
41             while (my ($key, $value) = each %hash) { ... } # not ok
42             foreach my $key (keys %hash) { my $value = $hash{$key}; ... } # ok
43              
44             =head1 AFFILIATION
45              
46             This policy is part of L<Perl::Critic::Freenode>.
47              
48             =head1 CONFIGURATION
49              
50             This policy is not configurable except for the standard options.
51              
52             =head1 AUTHOR
53              
54             Dan Book, C<dbook@cpan.org>
55              
56             =head1 COPYRIGHT AND LICENSE
57              
58             Copyright 2015, Dan Book.
59              
60             This library is free software; you may redistribute it and/or modify it under
61             the terms of the Artistic License version 2.0.
62              
63             =head1 SEE ALSO
64              
65             L<Perl::Critic>, L<http://blogs.perl.org/users/rurban/2014/04/do-not-use-each.html>