File Coverage

lib/Algorithm/MasterMind/Evolutionary.pm
Criterion Covered Total %
statement 15 15 100.0
branch n/a
condition n/a
subroutine 5 5 100.0
pod n/a
total 20 20 100.0


line stmt bran cond sub pod time code
1             package Algorithm::MasterMind::Evolutionary;
2              
3 2     2   1030 use warnings;
  2         4  
  2         71  
4 2     2   10 use strict;
  2         6  
  2         72  
5 2     2   10 use Carp;
  2         3  
  2         175  
6              
7 2         12 use lib qw(../../lib ../../../../Algorithm-Evolutionary/lib/
8             ../../../lib
9 2     2   10 ../../Algorithm-Evolutionary/lib/);
  2         3  
10              
11             our $VERSION = sprintf "%d.%03d", q$Revision: 1.8 $ =~ /(\d+)\.(\d+)/g;
12              
13 2     2   730 use base 'Algorithm::MasterMind::Evolutionary_Base';
  2         3  
  2         1369  
14              
15             use Algorithm::Evolutionary::Op::String_Mutation;
16             use Algorithm::Evolutionary::Op::Permutation;
17             use Algorithm::Evolutionary::Op::Uniform_Crossover;
18             use Algorithm::Evolutionary::Op::Easy;
19             use Algorithm::Evolutionary::Individual::String;
20              
21             # ---------------------------------------------------------------------------
22              
23              
24             sub initialize {
25             my $self = shift;
26             my $options = shift;
27             for my $o ( keys %$options ) {
28             $self->{"_$o"} = $options->{$o};
29             }
30              
31             # Variation operators
32             my $m = new Algorithm::Evolutionary::Op::String_Mutation; # Rate = 1
33             my $p = new Algorithm::Evolutionary::Op::Permutation; # Rate = 1
34             my $crossover_probability = 0.5;
35             my $crossover_rate = 3;
36             my $c = Algorithm::Evolutionary::Op::Uniform_Crossover->new( $crossover_probability,
37             $crossover_rate );
38              
39             my $fitness = sub { $self->fitness_orig(@_) };
40             my $ga = new Algorithm::Evolutionary::Op::Easy( $fitness,
41             $options->{'replacement_rate'},
42             [ $m, $p, $c] );
43             $self->{'_fitness'} = $fitness;
44             $self->{'_ga'} = $ga;
45              
46             }
47              
48              
49             sub issue_next {
50             my $self = shift;
51             my $rules = $self->number_of_rules();
52             my @alphabet = @{$self->{'_alphabet'}};
53             my $length = $self->{'_length'};
54             my $pop = $self->{'_pop'};
55             my $ga = $self->{'_ga'};
56             map( $_->evaluate( $self->{'_fitness'}), @$pop );
57             my @ranked_pop = sort { $b->{_fitness} <=> $a->{_fitness}; } @$pop;
58              
59             if ( $ranked_pop[0]->{'_matches'} == $rules ) { #Already found!
60             return $self->{'_last'} = $ranked_pop[0]->{'_str'};
61             } else {
62             my @pop_by_matches;
63             my $best;
64             do {
65             $ga->apply( $pop );
66             print "PoblaciĆ³n ", scalar @$pop, "\n";
67             map( $_->{'_matches'} = $_->{'_matches'}?$_->{'_matches'}:-1, @$pop ); #To avoid warnings
68             @pop_by_matches = sort { $b->{'_matches'} <=> $a->{'_matches'} } @$pop;
69             $best = $pop_by_matches[0];
70             } while ( $best->{'_matches'} < $rules );
71             return $self->{'_last'} = $best->{'_str'};
72             }
73              
74             }
75              
76             "some blacks, 0 white"; # Magic true value required at end of module
77              
78             __END__