Completed
Push — master ( ff5cab...a135cc )
by
unknown
17s queued 13s
created

AgingIndividualJDE.__init__()   A

Complexity

Conditions 1

Size

Total Lines 11
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 3
nop 2
dl 0
loc 11
rs 10
c 0
b 0
f 0
1
# encoding=utf8
2
import logging
3
4
from NiaPy.algorithms.algorithm import Individual
5
from NiaPy.algorithms.basic.de import DifferentialEvolution, CrossBest1, CrossRand1, CrossCurr2Best1, CrossBest2, CrossCurr2Rand1, proportional, multiMutations, DynNpDifferentialEvolution
6
from NiaPy.util.utility import objects2array
7
8
logging.basicConfig()
9
logger = logging.getLogger('NiaPy.algorithms.modified')
10
logger.setLevel('INFO')
11
12
__all__ = [
13
	'SelfAdaptiveDifferentialEvolution',
14
	'DynNpSelfAdaptiveDifferentialEvolutionAlgorithm',
15
	'AgingSelfAdaptiveDifferentialEvolution',
16
	'MultiStrategySelfAdaptiveDifferentialEvolution',
17
	'DynNpMultiStrategySelfAdaptiveDifferentialEvolution'
18
]
19
20
class SolutionjDE(Individual):
21
	r"""Individual for jDE algorithm.
22
23
	Attributes:
24
		F (float): Scale factor.
25
		CR (float): Crossover probability.
26
27
	See Also:
28
		:class:`NiaPy.algorithms.Individual`
29
	"""
30
	def __init__(self, F=2, CR=0.5, **kwargs):
31
		r"""Initialize SolutionjDE.
32
33
		Attributes:
34
			F (float): Scale factor.
35
			CR (float): Crossover probability.
36
37
		See Also:
38
			:func:`NiaPy.algorithm.Individual.__init__`
39
		"""
40
		Individual.__init__(self, **kwargs)
41
		self.F, self.CR = F, CR
42
43
class SelfAdaptiveDifferentialEvolution(DifferentialEvolution):
44
	r"""Implementation of Self-adaptive differential evolution algorithm.
45
46
	Algorithm:
47
		Self-adaptive differential evolution algorithm
48
49
	Date:
50
		2018
51
52
	Author:
53
		Uros Mlakar and Klemen Berkovič
54
55
	License:
56
		MIT
57
58
	Reference paper:
59
		Brest, J., Greiner, S., Boskovic, B., Mernik, M., Zumer, V. Self-adapting control parameters in differential evolution: A comparative study on numerical benchmark problems. IEEE transactions on evolutionary computation, 10(6), 646-657, 2006.
60
61
	Attributes:
62
		Name (List[str]): List of strings representing algorithm name
63
		F_l (float): Scaling factor lower limit.
64
		F_u (float): Scaling factor upper limit.
65
		Tao1 (float): Change rate for F parameter update.
66
		Tao2 (float): Change rate for CR parameter update.
67
68
	See Also:
69
		* :class:`NiaPy.algorithms.basic.DifferentialEvolution`
70
	"""
71
	Name = ['SelfAdaptiveDifferentialEvolution', 'jDE']
72
73
	@staticmethod
74
	def algorithmInfo():
75
		r"""Get algorithm information.
76
77
		Returns:
78
			str: Algorithm information.
79
80
		See Also:
81
			* :func:`NiaPy.algorithms.Algorithm.algorithmInfo`
82
		"""
83
		return r"""Brest, J., Greiner, S., Boskovic, B., Mernik, M., Zumer, V. Self-adapting control parameters in differential evolution: A comparative study on numerical benchmark problems. IEEE transactions on evolutionary computation, 10(6), 646-657, 2006."""
84
85 View Code Duplication
	@staticmethod
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
86
	def typeParameters():
87
		r"""Get dictionary with functions for checking values of parameters.
88
89
		Returns:
90
			Dict[str, Callable]:
91
				* F_l (Callable[[Union[float, int]], bool])
92
				* F_u (Callable[[Union[float, int]], bool])
93
				* Tao1 (Callable[[Union[float, int]], bool])
94
				* Tao2 (Callable[[Union[float, int]], bool])
95
96
		See Also:
97
			* :func:`NiaPy.algorithms.basic.DifferentialEvolution.typeParameters`
98
		"""
99
		d = DifferentialEvolution.typeParameters()
100
		d['F_l'] = lambda x: isinstance(x, (float, int)) and x > 0
101
		d['F_u'] = lambda x: isinstance(x, (float, int)) and x > 0
102
		d['Tao1'] = lambda x: isinstance(x, (float, int)) and 0 <= x <= 1
103
		d['Tao2'] = lambda x: isinstance(x, (float, int)) and 0 <= x <= 1
104
		return d
105
106
	def setParameters(self, F_l=0.0, F_u=1.0, Tao1=0.4, Tao2=0.2, **ukwargs):
107
		r"""Set the parameters of an algorithm.
108
109
		Arguments:
110
			F_l (Optional[float]): Scaling factor lower limit.
111
			F_u (Optional[float]): Scaling factor upper limit.
112
			Tao1 (Optional[float]): Change rate for F parameter update.
113
			Tao2 (Optional[float]): Change rate for CR parameter update.
114
115
		See Also:
116
			* :func:`NiaPy.algorithms.basic.DifferentialEvolution.setParameters`
117
		"""
118
		DifferentialEvolution.setParameters(self, itype=ukwargs.pop('itype', SolutionjDE), **ukwargs)
119
		self.F_l, self.F_u, self.Tao1, self.Tao2 = F_l, F_u, Tao1, Tao2
120
121
	def getParameters(self):
122
		r"""TODO.
123
124
		Returns:
125
			Dict[str, Any]: TODO.
126
		"""
127
		d = DifferentialEvolution.getParameters(self)
128
		d.update({
129
			'F_l': self.F_l,
130
			'F_u': self.F_u,
131
			'Tao1': self.Tao1,
132
			'Tao2': self.Tao2
133
		})
134
		return d
135
136
	def AdaptiveGen(self, x):
137
		r"""Adaptive update scale factor in crossover probability.
138
139
		Args:
140
			x (Individual): Individual to apply function on.
141
142
		Returns:
143
			Individual: New individual with new parameters
144
		"""
145
		f = self.F_l + self.rand() * (self.F_u - self.F_l) if self.rand() < self.Tao1 else x.F
146
		cr = self.rand() if self.rand() < self.Tao2 else x.CR
147
		return self.itype(x=x.x, F=f, CR=cr, e=False)
148
149
	def evolve(self, pop, xb, task, **ukwargs):
150
		r"""Evolve current population.
151
152
		Args:
153
			pop (numpy.ndarray[Individual]): Current population.
154
			xb (Individual): Global best individual.
155
			task (Task): Optimization task.
156
			ukwargs (Dict[str, Any]): Additional arguments.
157
158
		Returns:
159
			numpy.ndarray: New population.
160
		"""
161
		npop = objects2array([self.AdaptiveGen(e) for e in pop])
162
		for i, e in enumerate(npop): npop[i].x = self.CrossMutt(npop, i, xb, e.F, e.CR, rnd=self.Rand)
163
		for e in npop: e.evaluate(task, rnd=self.rand)
164
		return npop
165
166
class AgingIndividualJDE(SolutionjDE):
167
	r"""Individual with age.
168
169
	Attributes:
170
		age (int): Age of individual.
171
172
	See Also:
173
		* :func:`NiaPy.algorithms.modified.SolutionjDE`
174
	"""
175
	def __init__(self, **kwargs):
176
		r"""Initialize aging individual for jDE algorithm.
177
178
		Args:
179
			**kwargs (Dict[str, Any]): Additional arguments.
180
181
		See Also:
182
			* :func:`NiaPy.algorithms.modified.SolutionjDE.__init__`
183
		"""
184
		SolutionjDE.__init__(self, **kwargs)
185
		self.age = 0
186
187
class AgingSelfAdaptiveDifferentialEvolution(SelfAdaptiveDifferentialEvolution):
188
	r"""Implementation of Dynamic population size with aging self-adaptive differential evolution algorithm.
189
190
	Algorithm:
191
		Dynamic population size with aging self-adaptive self adaptive differential evolution algorithm
192
193
	Date:
194
		2018
195
196
	Author:
197
		Jan Popič and Klemen Berkovič
198
199
	License:
200
		MIT
201
202
	Reference URL:
203
		https://link.springer.com/article/10.1007/s10489-007-0091-x
204
205
	Reference paper:
206
		Brest, Janez, and Mirjam Sepesy Maučec. Population size reduction for the differential evolution algorithm. Applied Intelligence 29.3 (2008): 228-247.
207
208
	Attributes:
209
		Name (List[str]): List of strings representing algorithm name.
210
	"""
211
	Name = ['AgingSelfAdaptiveDifferentialEvolution', 'ANpjDE']
212
213
	@staticmethod
214
	def algorithmInfo():
215
		r"""Get basic information about the algorithm.
216
217
		Returns:
218
			str: Basic information.
219
220
		See Also:
221
			* :func:`NiaPy.algorithms.Algorithm.algorithmInfo`
222
		"""
223
		return r"""Brest, Janez, and Mirjam Sepesy Maučec. Population size reduction for the differential evolution algorithm. Applied Intelligence 29.3 (2008): 228-247."""
224
225
	@staticmethod
226
	def typeParameters():
227
		d = SelfAdaptiveDifferentialEvolution.typeParameters()
228
		# TODO
229
		return d
230
231
	def setParameters(self, LT_min=1, LT_max=7, age=proportional, **ukwargs):
232
		r"""Set core parameters of AgingSelfAdaptiveDifferentialEvolution algorithm.
233
234
		Args:
235
			LT_min (Optional[int]): Minimum age.
236
			LT_max (Optional[int]): Maximum age.
237
			age (Optional[Callable[[], int]]): Function for calculating age of individual.
238
			**ukwargs (Dict[str, Any]): Additional arguments.
239
240
		See Also:
241
			* :func:`SelfAdaptiveDifferentialEvolution.setParameters`
242
		"""
243
		SelfAdaptiveDifferentialEvolution.setParameters(self, **ukwargs)
244
		self.LT_min, self.LT_max, self.age = LT_min, LT_max, age
245
		self.mu = abs(self.LT_max - self.LT_min) / 2
246
247
class DynNpSelfAdaptiveDifferentialEvolutionAlgorithm(SelfAdaptiveDifferentialEvolution, DynNpDifferentialEvolution):
248
	r"""Implementation of Dynamic population size self-adaptive differential evolution algorithm.
249
250
	Algorithm:
251
		Dynamic population size self-adaptive differential evolution algorithm
252
253
	Date:
254
		2018
255
256
	Author:
257
		Jan Popič and Klemen Berkovič
258
259
	License:
260
		MIT
261
262
	Reference URL:
263
		https://link.springer.com/article/10.1007/s10489-007-0091-x
264
265
	Reference paper:
266
		Brest, Janez, and Mirjam Sepesy Maučec. Population size reduction for the differential evolution algorithm. Applied Intelligence 29.3 (2008): 228-247.
267
268
	Attributes:
269
		Name (List[str]): List of strings representing algorithm name.
270
		rp (int): Small non-negative number which is added to value of generations.
271
		pmax (int): Number of population reductions.
272
273
	See Also:
274
		* :class:`NiaPy.algorithms.modified.SelfAdaptiveDifferentialEvolution`
275
	"""
276
	Name = ['DynNpSelfAdaptiveDifferentialEvolutionAlgorithm', 'dynNPjDE']
277
278
	@staticmethod
279
	def algorithmInfo():
280
		r"""Get basic information about the algorithm.
281
282
		Returns:
283
			str: Basic information.
284
285
		See Also:
286
			* :func:`NiaPy.algorithms.Algorithm.algorithmInfo`
287
		"""
288
		return r"""Brest, Janez, and Mirjam Sepesy Maučec. Population size reduction for the differential evolution algorithm. Applied Intelligence 29.3 (2008): 228-247."""
289
290
	@staticmethod
291
	def typeParameters():
292
		r"""Get basic information of algorithm.
293
294
		Returns:
295
			str: Basic information of algorithm.
296
297
		See Also:
298
			* :func:`NiaPy.algorithms.Algorithm.algorithmInfo`
299
		"""
300
		d = SelfAdaptiveDifferentialEvolution.typeParameters()
301
		d['rp'] = lambda x: isinstance(x, (float, int)) and x > 0
302
		d['pmax'] = lambda x: isinstance(x, int) and x > 0
303
		return d
304
305
	def setParameters(self, rp=0, pmax=10, **ukwargs):
306
		r"""Set the parameters of an algorithm.
307
308
		Arguments:
309
			rp (Optional[int]): Small non-negative number which is added to value of genp (if it's not divisible).
310
			pmax (Optional[int]): Number of population reductions.
311
312
		See Also:
313
			* :func:`NiaPy.algorithms.modified.SelfAdaptiveDifferentialEvolution.setParameters`
314
		"""
315
		DynNpDifferentialEvolution.setParameters(self, rp=rp, pmax=pmax, **ukwargs)
316
		SelfAdaptiveDifferentialEvolution.setParameters(self, **ukwargs)
317
318
	def postSelection(self, pop, task, **kwargs):
319
		r"""Post selection operator.
320
321
		Args:
322
			pop (numpy.ndarray[Individual]): Current population.
323
			task (Task): Optimization task.
324
325
		Returns:
326
			numpy.ndarray[Individual]: New population.
327
		"""
328
		return DynNpDifferentialEvolution.postSelection(self, pop, task, **kwargs)
329
330
class MultiStrategySelfAdaptiveDifferentialEvolution(SelfAdaptiveDifferentialEvolution):
331
	r"""Implementation of self-adaptive differential evolution algorithm with multiple mutation strategys.
332
333
	Algorithm:
334
		Self-adaptive differential evolution algorithm with multiple mutation strategys
335
336
	Date:
337
		2018
338
339
	Author:
340
		Klemen Berkovič
341
342
	License:
343
		MIT
344
345
	Attributes:
346
		Name (List[str]): List of strings representing algorithm name
347
348
	See Also:
349
		* :class:`NiaPy.algorithms.modified.SelfAdaptiveDifferentialEvolution`
350
	"""
351
	Name = ['MultiStrategySelfAdaptiveDifferentialEvolution', 'MsjDE']
352
353
	def setParameters(self, strategies=(CrossCurr2Rand1, CrossCurr2Best1, CrossRand1, CrossBest1, CrossBest2), **kwargs):
354
		r"""Set core parameters of MultiStrategySelfAdaptiveDifferentialEvolution algorithm.
355
356
		Args:
357
			strategys (Optional[Iterable[Callable]]): Mutations strategies to use in algorithm.
358
			**kwargs:
359
360
		See Also:
361
			* :func:`NiaPy.algorithms.modified.SelfAdaptiveDifferentialEvolution.setParameters`
362
		"""
363
		SelfAdaptiveDifferentialEvolution.setParameters(self, CrossMutt=kwargs.pop('CrossMutt', multiMutations), **kwargs)
364
		self.strategies = strategies
365
366 View Code Duplication
	def evolve(self, pop, xb, task, **kwargs):
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
367
		r"""Evolve population with the help multiple mutation strategies.
368
369
		Args:
370
			pop (numpy.ndarray[Individual]): Current population.
371
			xb (Individual): Current best individual.
372
			task (Task): Optimization task.
373
			**kwargs (Dict[str, Any]): Additional arguments.
374
375
		Returns:
376
			numpy.ndarray[Individual]: New population of individuals.
377
		"""
378
		return objects2array([self.CrossMutt(pop, i, xb, self.F, self.CR, self.Rand, task, self.itype, self.strategies) for i in range(len(pop))])
379
380
class DynNpMultiStrategySelfAdaptiveDifferentialEvolution(MultiStrategySelfAdaptiveDifferentialEvolution, DynNpSelfAdaptiveDifferentialEvolutionAlgorithm):
381
	r"""Implementation of Dynamic population size self-adaptive differential evolution algorithm with multiple mutation strategies.
382
383
	Algorithm:
384
		Dynamic population size self-adaptive differential evolution algorithm with multiple mutation strategies
385
386
	Date:
387
		2018
388
389
	Author:
390
		Klemen Berkovič
391
392
	License:
393
		MIT
394
395
	Attributes:
396
		Name (List[str]): List of strings representing algorithm name.
397
398
	See Also:
399
		* :class:`NiaPy.algorithms.modified.MultiStrategySelfAdaptiveDifferentialEvolution`
400
		* :class:`NiaPy.algorithms.modified.DynNpSelfAdaptiveDifferentialEvolutionAlgorithm`
401
	"""
402
	Name = ['DynNpMultiStrategySelfAdaptiveDifferentialEvolution', 'dynNpMsjDE']
403
404
	def setParameters(self, pmax=10, rp=5, **kwargs):
405
		r"""Set core parameters for algorithm instance.
406
407
		Args:
408
			pmax (Optional[int]):
409
			rp (Optional[int]):
410
			**kwargs (Dict[str, Any]):
411
412
		See Also:
413
			* :func:`NiaPy.algorithms.modified.MultiStrategySelfAdaptiveDifferentialEvolution.setParameters`
414
		"""
415
		MultiStrategySelfAdaptiveDifferentialEvolution.setParameters(self, **kwargs)
416
		self.pmax, self.rp = pmax, rp
417
418
	def postSelection(self, pop, task, **kwargs):
419
		return DynNpSelfAdaptiveDifferentialEvolutionAlgorithm.postSelection(self, pop, task)
420
421
# vim: tabstop=3 noexpandtab shiftwidth=3 softtabstop=3
422