IndicatorBasedSelection.h
Go to the documentation of this file.
1 /*!
2  *
3  *
4  * \brief Indicator-based selection strategy for multi-objective selection.
5  *
6  *
7  *
8  * \author T.Voss
9  * \date 2010
10  *
11  *
12  * \par Copyright 1995-2017 Shark Development Team
13  *
14  * <BR><HR>
15  * This file is part of Shark.
16  * <http://shark-ml.org/>
17  *
18  * Shark is free software: you can redistribute it and/or modify
19  * it under the terms of the GNU Lesser General Public License as published
20  * by the Free Software Foundation, either version 3 of the License, or
21  * (at your option) any later version.
22  *
23  * Shark is distributed in the hope that it will be useful,
24  * but WITHOUT ANY WARRANTY; without even the implied warranty of
25  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26  * GNU Lesser General Public License for more details.
27  *
28  * You should have received a copy of the GNU Lesser General Public License
29  * along with Shark. If not, see <http://www.gnu.org/licenses/>.
30  *
31  */
32 #ifndef SHARK_ALGORITHMS_DIRECT_SEARCH_OPERATORS_SELECTION_INDICATOR_BASED_SELECTION_H
33 #define SHARK_ALGORITHMS_DIRECT_SEARCH_OPERATORS_SELECTION_INDICATOR_BASED_SELECTION_H
34 
36 
37 #include <map>
38 #include <vector>
39 
40 namespace shark {
41 
42 /**
43 * \brief Implements the well-known indicator-based selection strategy.
44 *
45 * See
46 * Kalyanmoy Deb and Amrit Pratap and Sameer Agarwal and T. Meyarivan,
47 * A Fast Elitist Multi-Objective Genetic Algorithm: NSGA-II,
48 * IEEE Transactions on Evolutionary Computation
49 * Year 2000, Volume 6, p. 182-197
50 *
51 * \tparam Indicator The second-level sorting criterion.
52 */
53 template<typename Indicator>
55  /**
56  * \brief Executes the algorithm and assigns each member of the population
57  * its level non-dominance (rank) and its individual contribution to the front
58  * it belongs to (share).
59  *
60  * \param [in,out] population The population to be ranked.
61  * \param [in,out] mu the number of individuals to select
62  */
63  template<typename PopulationType>
64  void operator()( PopulationType & population, std::size_t mu ){
65  if(population.empty()) return;
66 
67  //perform a nondominated sort to assign the rank to every element
68  nonDominatedSort(penalizedFitness(population), ranks(population));
69 
70  typedef std::vector< view_reference<typename PopulationType::value_type > > View;
71 
72  unsigned int maxRank = 0;
73  std::map< unsigned int, View > fronts;
74 
75  for( unsigned int i = 0; i < population.size(); i++ ) {
76  maxRank = std::max( maxRank, population[i].rank());
77  fronts[population[i].rank()].push_back( population[i] );
78  population[i].selected() = true;
79  }
80 
81  //deselect the highest rank fronts until we would end up with less or equal mu elements
82  unsigned int rank = maxRank;
83  std::size_t popSize = population.size();
84 
85  while(popSize-fronts[rank].size() >= mu){
86  //deselect all elements in this front
87  View & front = fronts[rank];
88  for(std::size_t i = 0; i != front.size(); ++i){
89  front[i].selected() = false;
90  }
91  popSize -= front.size();
92  --rank;
93  }
94  //now use the indicator to deselect the worst approximating elements of the last selected front
95  View& front = fronts[rank];
96 
97  //create an archive of points which are surely selected because of their domination rank
98  View archive;
99  archive.reserve(popSize - front.size());
100  for(unsigned int r = 1; r != rank; ++r){
101  archive.insert(archive.end(),fronts[r].begin(), fronts[r].end());
102  }
103  //deselect
104  std::vector<std::size_t> deselected = m_indicator.leastContributors(penalizedFitness(front),penalizedFitness(archive), popSize - mu);
105  for(auto lc:deselected){
106  front[lc].selected() = false;
107  }
108  }
109 
110  /**
111  * \brief Stores/restores the serializer's state.
112  * \tparam Archive Type of the archive.
113  * \param [in,out] archive The archive to serialize to.
114  * \param [in] version number, currently unused.
115  */
116  template<typename Archive>
117  void serialize( Archive & archive, const unsigned int version )
118  {
119  archive & BOOST_SERIALIZATION_NVP( m_indicator );
120  }
121  Indicator& indicator(){
122  return m_indicator;
123  }
124  Indicator const& indicator()const{
125  return m_indicator;
126  }
127 private:
128  Indicator m_indicator; ///< Instance of the second level sorting criterion.
129 
130  /** \cond */
131  template<typename T>
132  struct view_reference {
133  T * mep_value;
134  public:
135  typedef RealVector FitnessType;
136 
137  view_reference() : mep_value( NULL ){}
138  view_reference(T & value) : mep_value( &value ){}
139 
140  operator T & ()
141  {
142  return( *mep_value );
143  }
144 
145  operator const T & () const
146  {
147  return( *mep_value );
148  }
149 
150  view_reference<T> operator=( const T & rhs )
151  {
152  *mep_value = rhs;
153  return *this;
154  }
155 
156  RealVector& penalizedFitness() {
157  return mep_value->penalizedFitness();
158  }
159 
160  RealVector& unpenalizedFitness(){
161  return mep_value->unpenalizedFitness();
162  }
163 
164  RealVector const& penalizedFitness() const{
165  return mep_value->penalizedFitness();
166  }
167 
168  RealVector const& unpenalizedFitness() const{
169  return mep_value->unpenalizedFitness();
170  }
171 
172  bool& selected(){
173  return mep_value->selected();
174  }
175  };
176  /** \endcond */
177 };
178 }
179 
180 #endif