pypharm 1.3.3__tar.gz → 1.3.5__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: pypharm
3
- Version: 1.3.3
3
+ Version: 1.3.5
4
4
  Summary: Module for solving pharmacokinetic problems
5
5
  Home-page: https://github.com/Krash13/PyPharm
6
6
  Author: Krash13
@@ -139,6 +139,75 @@ model.optimize(
139
139
  При оптимизации, вектор неизвестных это
140
140
  x = [configuration_matrix (неизвестные), outputs(неизвестные), volumes(неизвестные)]
141
141
 
142
+ Кроме того, вы можете использовать генетический алгоритм:
143
+ ```python
144
+ model.optimize(
145
+ method='GA',
146
+ x_min=[0.00001, 0.001, 0.01, 1, 1],
147
+ x_max=[1, 2, 1, 10, 3],
148
+ genes=[16, 17, 16, 20, 16],
149
+ n=100,
150
+ child_percent=0.3,
151
+ mutation_chance=0.5,
152
+ max_mutation=5,
153
+ t_max=300,
154
+ max_step=0.5,
155
+ printing=True,
156
+ )
157
+ ```
158
+
159
+ Вы даже можете использовать свой собственный алгоритм, если это необходимо
160
+
161
+ ```python
162
+ # CountriesAlgorithm - ваш класс алгоритма
163
+ # start - функция запуска алгоритма
164
+ # важно, чтобы ваша функция запуска возвращала numpy.array
165
+
166
+ model.optimize(
167
+ user_method=CountriesAlgorithm,
168
+ method_is_func=False,
169
+ optimization_func_name='start',
170
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], #ваши настроечные параметры
171
+ Xmax=[1, 2, 1, 10, 3],
172
+ genes=[16, 17, 16, 20, 16],
173
+ M=20,
174
+ N=25,
175
+ n=[1, 10],
176
+ max_mutation=8,
177
+ m=[1, 8],
178
+ k=8,
179
+ l=3,
180
+ ep=[0.2, 0.4],
181
+ tmax=200,
182
+ max_step=0.5,
183
+ printing=True
184
+ )
185
+ ```
186
+
187
+ или
188
+
189
+ ```python
190
+ # my_alg - ваша функция алгоритма, важно, чтобы она принимала только целевую функцию
191
+
192
+ model.optimize(
193
+ user_method=my_alg,
194
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], #ваши настроечные параметры
195
+ Xmax=[1, 2, 1, 10, 3],
196
+ genes=[16, 17, 16, 20, 16],
197
+ M=20,
198
+ N=25,
199
+ n=[1, 10],
200
+ max_mutation=8,
201
+ m=[1, 8],
202
+ k=8,
203
+ l=3,
204
+ ep=[0.2, 0.4],
205
+ tmax=200,
206
+ max_step=0.5,
207
+ printing=True
208
+ )
209
+ ```
210
+
142
211
  **4) Модель MagicCompartmentModel**
143
212
 
144
213
  Данная модель необходима нам для тех случаев,
@@ -345,6 +414,77 @@ printing=True,
345
414
  When optimizing, the vector of unknowns is
346
415
  x = [configuration_matrix (unknown), outputs(unknown), volumes(unknown)]
347
416
 
417
+ In addition, you can use a genetic algorithm:
418
+
419
+ ```python
420
+
421
+ model.optimize(
422
+ method='GA',
423
+ x_min=[0.00001, 0.001, 0.01, 1, 1],
424
+ x_max=[1, 2, 1, 10, 3],
425
+ genes=[16, 17, 16, 20, 16],
426
+ n=100,
427
+ percentage of descendants=0.3,
428
+ the probability of mutation =0.5,
429
+ max_mutation=5,
430
+ t_max=300,
431
+ max_step=0.5,
432
+ print=True,
433
+ )
434
+ ```
435
+
436
+ You can even use your own algorithm if necessary.
437
+
438
+ ```python
439
+ # Countryalgorithm - your class is an algorithm
440
+ # start - start the algorithm
441
+ # it is important that your application aroused the interest of numpy.array
442
+
443
+ model.optimize(
444
+ user_method=country Countryalgorithm,
445
+ method_is_func=False,
446
+ optimization_func_name='start',
447
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], # your desktop settings
448
+ Xmax Max=[1, 2, 1, 10, 3],
449
+ genes=[16, 17, 16, 20, 16],
450
+ M=20,
451
+ N=25,
452
+ n=[1, 10],
453
+ max_mutation=8,
454
+ m=[1, 8],
455
+ k=8,
456
+ l=3,
457
+ ep=[0,2, 0,4],
458
+ tmax=200,
459
+ max_step=0.5,
460
+ print=True
461
+ )
462
+ ```
463
+
464
+ or
465
+
466
+ ```python
467
+ # my_alg is your algorithm function, it is important that it accepts only the target function
468
+
469
+ model.optimize(
470
+ custom method=my_alg,
471
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], # your desktop settings
472
+ Xmax Max=[1, 2, 1, 10, 3],
473
+ genes=[16, 17, 16, 20, 16],
474
+ M=20,
475
+ N=25,
476
+ n=[1, 10],
477
+ max_mutation=8,
478
+ m=[1, 8],
479
+ k=8,
480
+ l=3,
481
+ ep=[0,2, 0,4],
482
+ tmax=200,
483
+ max_step=0.5,
484
+ print=True
485
+ )
486
+ ```
487
+
348
488
  **4) The MagicCompartmentModel model**
349
489
 
350
490
  We need this model for those cases
@@ -2,7 +2,6 @@ import random
2
2
  import numpy as np
3
3
  from operator import attrgetter
4
4
  from math import ceil, cos, sin
5
- from multiprocessing import shared_memory
6
5
 
7
6
 
8
7
  class Individual:
@@ -469,35 +468,3 @@ class CountriesAlgorithm:
469
468
  self.memory_list[-1] = float(result.f)
470
469
  return (result.x, result.f, False, ti)
471
470
 
472
-
473
-
474
- # def func(x):
475
- # s = 0
476
- # for i in range(len(x) - 1):
477
- # s += -x[i] * np.sin(abs(x[i] - x[i+1] - 47) ** 0.5) - (x[i+1] + 47) * np.sin(abs(x[i+1] + x[i] / 2 + 47) ** 0.5)
478
- # return s
479
- #
480
- # k = 0
481
- # for i in range(100):
482
- # CA = CountriesAlgorithm(
483
- # f=func,
484
- # Xmin=[-512 for i in range(3)],
485
- # Xmax=[512 for i in range(3)],
486
- # M=100,
487
- # N=15,
488
- # n=[1, 10],
489
- # p=[0.00001, 2.5],
490
- # m=[1, 8],
491
- # k=8,
492
- # l=3,
493
- # ep=[0.2, 0.4],
494
- # tmax=300,
495
- # printing=False,
496
- # teoretic_y=-1888.3213909
497
- # )
498
- # r = CA.start()
499
- # print(i, r[2], r[0], r[1])
500
- # if r[2]:
501
- # k += 1
502
- #
503
- # print(k/100)
@@ -0,0 +1,426 @@
1
+ import random
2
+ import numpy as np
3
+ import copy
4
+ from operator import attrgetter
5
+ from math import ceil, cos, sin
6
+ import graycode
7
+
8
+ def rand_str():
9
+ s = 'qwertyuiopasdfghjklzxcvbnm'
10
+ k = np.random.choice(len(s), 8, replace=False)
11
+ res = ''
12
+ for ki in k:
13
+ res += s[ki]
14
+ return res
15
+
16
+ def check_population(country):
17
+ return bool(country.population.size)
18
+
19
+ vector_check_population = np.vectorize(check_population, signature='()->()')
20
+
21
+ class Individual:
22
+
23
+ def __init__(self, gray_code, x_min, x_max, genes, function):
24
+
25
+ self.x_min = x_min
26
+ self.x_max = x_max
27
+ self.genes = genes
28
+ self.function = function
29
+ self.steps = (self.x_max - self.x_min) / (2 ** (self.genes) - 1)
30
+ self.gray_code = gray_code
31
+ self.f = self.function(self.real_x)
32
+ self.ep_n = 0
33
+
34
+ @property
35
+ def real_x(self):
36
+ decimal_x = []
37
+ gray_code = copy.deepcopy(self.gray_code)
38
+ for g in self.genes:
39
+ decimal_x.append(graycode.gray_code_to_tc(int(gray_code[:g], base=2)))
40
+ gray_code = gray_code[g:]
41
+ return self.x_min + self.steps * np.array(decimal_x)
42
+
43
+ @property
44
+ def decimal_x(self):
45
+ return (self.real_x - self.x_min) / self.steps
46
+
47
+ @classmethod
48
+ def generate_from_decimal(cls, decimal, x_min, x_max, genes, function):
49
+ gray_code = ''
50
+ decimal = np.clip(decimal, np.zeros(decimal.size), 2 ** (genes) - 1)
51
+ for i in range(len(decimal)):
52
+ s = '{:0' + str(genes[i]) + 'b}'
53
+ gray_code += s.format(graycode.tc_to_gray_code(int(decimal[i])))
54
+
55
+ return cls(gray_code, x_min, x_max, genes, function)
56
+
57
+ def mutation(self, max_mutation=1):
58
+ n = max(0, max_mutation - self.ep_n)
59
+ if n:
60
+ gray_code = copy.deepcopy(self.gray_code)
61
+ k = np.random.choice(len(gray_code), n, replace=False)
62
+ for ki in k:
63
+ b = bool(int(gray_code[ki]))
64
+ b = not b
65
+ b = str(int(b))
66
+ gray_code = gray_code[:ki] + b + gray_code[ki+1:]
67
+ return Individual(gray_code, self.x_min, self.x_max, self.genes, self.function)
68
+ else:
69
+ return self
70
+
71
+ @classmethod
72
+ def crossover(cls, individual1, individual2):
73
+ k = np.random.randint(1, len(individual1.gray_code) - 1, 2)
74
+ while k[0] == k[1]:
75
+ k = np.random.randint(1, len(individual1.gray_code) - 1, 2)
76
+ k = np.sort(k)
77
+ new_gray1 = individual1.gray_code[:k[0]] + individual2.gray_code[k[0]:k[1]] + individual1.gray_code[k[1]:]
78
+ new_gray2 = individual2.gray_code[:k[0]] + individual1.gray_code[k[0]:k[1]] + individual2.gray_code[k[1]:]
79
+ return [
80
+ cls(new_gray1, individual1.x_min, individual1.x_max, individual1.genes, individual1.function),
81
+ cls(new_gray2, individual1.x_min, individual1.x_max, individual1.genes, individual1.function),
82
+ ]
83
+
84
+ def __lt__(self, other):
85
+ return self.f < other.f
86
+
87
+ def __le__(self, other):
88
+ return self.f <= other.f
89
+
90
+ def __gt__(self, other):
91
+ return self.f > other.f
92
+
93
+ def __ge__(self, other):
94
+ return self.f >= other.f
95
+
96
+
97
+ class Country:
98
+
99
+ def __init__(self, N, x_min, x_max, genes, function):
100
+ self.f = function
101
+ self.N = N
102
+ self.x_min = np.array(x_min)
103
+ self.x_max = np.array(x_max)
104
+ self.genes = np.array(genes)
105
+ self.name = rand_str()
106
+
107
+
108
+ local_xmin = np.random.randint(np.zeros(self.genes.size), 2 ** self.genes - 1)
109
+ local_xmax = np.random.randint(local_xmin, 2 ** self.genes)
110
+
111
+ self.rand_n_individual = np.vectorize(lambda x: x * self.random_individual(local_xmin, local_xmax), signature='()->(n)')
112
+ self.generate_population = np.vectorize(lambda decimal: Individual.generate_from_decimal(
113
+ decimal, self.x_min, self.x_max, self.genes, self.f), signature='(n)->()')
114
+
115
+ x = self.rand_n_individual(np.ones(self.N))
116
+ self.population = self.generate_population(x)
117
+
118
+
119
+ self.sort_population()
120
+ self.action = None
121
+ self.enemy = None
122
+ self.ally = None
123
+
124
+ def random_individual(self, x_min, x_max):
125
+ return np.random.randint(x_min, x_max)
126
+
127
+ @property
128
+ def best_function(self):
129
+ return self.population[0].f
130
+
131
+ def roulette_function(self, f_min, f_max):
132
+ return (f_max - self.population[0].f) / (f_max - f_min)
133
+
134
+ @property
135
+ def avg_function(self):
136
+ return sum([individual.f for individual in self.population]) / self.population.size
137
+
138
+ def sort_population(self):
139
+ self.population.sort()
140
+
141
+ def reproduction(self, n_min, n_max, f_min, f_max):
142
+ n = ceil((n_max - n_min) * (f_max - self.avg_function) / (f_max - f_min) + n_min)
143
+ n = np.clip(n, n_min, n_max)
144
+ # p2 = (1 - ti / t_max) * (self.avg_function - f_min) / (f_max - f_min)
145
+ new_individuals = []
146
+
147
+ for i in range(n):
148
+ if len(self.population) == 2 and self.population[0] == self.population[1]:
149
+ new_individuals.extend(Individual.crossover(self.population[0], self.population[1],
150
+ self.x_min, self.x_max, self.genes, self.f))
151
+ continue
152
+ k1 = random.randint(0, len(self.population) - 1)
153
+ individual1 = self.population[k1]
154
+ k2 = k1
155
+ while k2 == k1:
156
+ k2 = random.randint(0, len(self.population) - 1)
157
+ individual2 = self.population[k2]
158
+ new_individuals += Individual.crossover(individual1, individual2)
159
+ self.population = np.append(self.population, np.array(new_individuals))
160
+ self.sort_population()
161
+
162
+ def extinction(self, m_min, m_max, f_min, f_max):
163
+ m = int((m_max - m_min) * (self.avg_function - f_min) / (f_max - f_min) + m_min)
164
+ m = np.clip(m, m_min, m_max)
165
+ self.population = self.population[:-m]
166
+
167
+ def extinction1(self, n):
168
+ if self.population.size < n:
169
+ return n - self.population.size
170
+ self.population = self.population[:n]
171
+ return 0
172
+
173
+ def select_action(self, countries):
174
+ self.action = random.randint(0, 3)
175
+ if self.action == 1:
176
+ ally_list = [country for country in countries if country.action is None and country != self]
177
+ if ally_list:
178
+ self.ally = ally_list.pop(random.randint(0, len(ally_list) - 1))
179
+ self.ally.action = 1
180
+ self.ally.ally = self
181
+ else:
182
+ self.action = random.choice([0, 3])
183
+ if self.action == 2:
184
+ enemy_list = [country for country in countries if country.action is None and country != self]
185
+ if enemy_list:
186
+ self.enemy = enemy_list.pop(random.randint(0, len(enemy_list) - 1))
187
+ self.enemy.action = 2
188
+ self.enemy.enemy = self
189
+ else:
190
+ self.action = random.choice([0, 3])
191
+
192
+ def epedemic(self, elite, dead, max_mutation):
193
+ if max_mutation < 1:
194
+ max_mutation = 1
195
+ n_elite = ceil(elite * len(self.population))
196
+ n_dead = ceil(dead * len(self.population))
197
+ self.population = self.population[:-n_dead]
198
+ for i in range(n_elite, self.population.size):
199
+ self.population[i] = self.population[i].mutation(max_mutation)
200
+ self.sort_population()
201
+ self.action = None
202
+
203
+ # def sabotage(self, n_copy):
204
+ # for i in range(n_copy):
205
+ # self.enemy.population.append(copy.copy(self.population[0]))
206
+ # self.action = None
207
+ # self.enemy = None
208
+
209
+ def motion(self):
210
+ x_best = self.population[0].decimal_x
211
+ for i in range(1, len(self.population)):
212
+ self.population[i] = Individual.generate_from_decimal(
213
+ self.population[i].decimal_x + np.int64(random.uniform(0, 2) * (x_best - self.population[i].decimal_x)), self.x_min, self.x_max, self.genes, self.f
214
+ )
215
+ self.sort_population()
216
+ self.action = None
217
+
218
+ @staticmethod
219
+ def trade(country1, country2, k):
220
+ if country1.population.size <= k or country2.population.size <= k:
221
+ k = min(country1.population.size, country2.population.size) // 2
222
+ indexes1 = np.random.choice(country1.population.size, k, replace=False)
223
+ indexes2 = np.random.choice(country2.population.size, k, replace=False)
224
+ country2.population = np.concatenate([country2.population, country1.population[indexes1]])
225
+ country1.population = np.concatenate([country1.population, country2.population[indexes2]])
226
+ country1.population = np.delete(country1.population, indexes1)
227
+ country2.population = np.delete(country2.population, indexes2)
228
+ country1.sort_population()
229
+ country2.sort_population()
230
+ country1.action = None
231
+ country2.action = None
232
+ country1.ally = None
233
+ country2.ally = None
234
+
235
+ @staticmethod
236
+ def war(country1, country2, l):
237
+ if country1.population.size <= l or country2.population.size <= l:
238
+ l = min(country1.population.size, country2.population.size)
239
+ indexes1 = np.random.choice(country1.population.size, l, replace=False)
240
+ indexes2 = np.random.choice(country2.population.size, l, replace=False)
241
+ war_list1 = country1.population[indexes1]
242
+ war_list2 = country2.population[indexes2]
243
+ country1.population = np.delete(country1.population, indexes1)
244
+ country2.population = np.delete(country2.population, indexes2)
245
+ wins1 = np.where(war_list1 > war_list2)
246
+ wins2 = np.where(war_list2 > war_list2)
247
+ if wins1[0].size > wins2[0].size:
248
+ np.concatenate([country1.population, war_list1])
249
+ np.concatenate([country1.population, war_list2])
250
+ elif wins2[0].size > wins1[0].size:
251
+ np.concatenate([country2.population, war_list1])
252
+ np.concatenate([country2.population, war_list2])
253
+ else:
254
+ np.concatenate([country1.population, war_list1])
255
+ np.concatenate([country2.population, war_list2])
256
+ country1.sort_population()
257
+ country2.sort_population()
258
+ country1.action = None
259
+ country2.action = None
260
+ country1.enemy = None
261
+ country2.enemy = None
262
+
263
+
264
+ class CountriesAlgorithm:
265
+
266
+ def __init__(self, f, Xmin, Xmax, genes, M, N, n, m, k, l, ep, max_mutation, tmax, printing=False, memory_list=None):
267
+ self.f = f
268
+ self.Xmin = Xmin
269
+ self.Xmax = Xmax
270
+ self.n = n
271
+ self.genes = genes
272
+ self.m = m
273
+ self.k = k
274
+ self.M = M
275
+ self.N = N
276
+ self.l = l
277
+ self.ep = ep
278
+ self.max_mutation = max_mutation
279
+ self.tmax = tmax
280
+ self.countries = []
281
+ self.printing = printing
282
+ self.memory_list = memory_list
283
+ for i in range(M):
284
+ self.countries.append(Country(N, self.Xmin, self.Xmax, self.genes, self.f))
285
+
286
+ def start(self):
287
+ ti = 0
288
+ motion = 0
289
+ trade = 0
290
+ war = 0
291
+ epedemic = 0
292
+ if self.memory_list is not None:
293
+ self.memory_list[0] = False
294
+ while ti <= self.tmax:
295
+ ti += 1
296
+ for country in self.countries:
297
+ if country.action is None:
298
+ country.select_action(self.countries)
299
+ for country in self.countries:
300
+ if country.action == 0:
301
+ motion += 1
302
+ country.motion( )
303
+ elif country.action == 1:
304
+ trade += 1
305
+ Country.trade(
306
+ country1=country,
307
+ country2=country.ally,
308
+ k=self.k
309
+ )
310
+ elif country.action == 2:
311
+ war += 1
312
+ Country.war(
313
+ country1=country,
314
+ country2=country.enemy,
315
+ l=self.l
316
+ )
317
+ elif country.action == 3:
318
+ epedemic += 1
319
+ country.epedemic(
320
+ elite=self.ep[0],
321
+ dead=self.ep[1],
322
+ max_mutation=int((1 - ti / self.tmax) * self.max_mutation),
323
+ )
324
+ indexes = np.where(vector_check_population(self.countries) == True)
325
+ self.countries = [self.countries[i] for i in indexes[0]]
326
+
327
+ self.countries = sorted(self.countries, key=attrgetter('avg_function'))
328
+ if not self.countries:
329
+ break
330
+ f_min = self.countries[0].avg_function
331
+ f_max = self.countries[-1].avg_function
332
+ if f_min == f_max:
333
+ self.countries = sorted(self.countries, key=attrgetter('best_function'))
334
+ result = self.countries[0].population[0]
335
+ break
336
+ e_individuals = []
337
+ for country in self.countries:
338
+ if len(country.population) == 1:
339
+ e_individuals.append(country.population[0])
340
+ continue
341
+ if country.population.size:
342
+ country.reproduction(
343
+ n_min=self.n[0],
344
+ n_max=self.n[1],
345
+ f_min=f_min,
346
+ f_max=f_max
347
+ )
348
+ # country.extinction(
349
+ # m_min=self.m[0],
350
+ # m_max=self.m[1],
351
+ # f_min=f_min,
352
+ # f_max=f_max
353
+ # )
354
+ self.countries = sorted(self.countries, key=attrgetter('best_function'))
355
+ f_min = self.countries[0].best_function
356
+ f_max = self.countries[-1].best_function
357
+ s = sum(country.roulette_function(f_min, f_max) for country in self.countries if len(country.population) > 1)
358
+ self.countries.reverse()
359
+ for country in self.countries:
360
+ plus = 0
361
+ if len(country.population) >= 1:
362
+ res = country.extinction1(
363
+ max(self.N // 2, ceil(country.roulette_function(f_min, f_max) / s * self.N * self.M)) + plus
364
+ )
365
+ if res:
366
+ plus += res
367
+ else:
368
+ plus = 0
369
+
370
+ indexes = np.where(vector_check_population(self.countries) == True)
371
+ self.countries = [self.countries[i] for i in indexes[0]]
372
+
373
+ for individual in e_individuals:
374
+ random_country = self.countries[random.randint(0, len(self.countries) - 1)]
375
+ np.append(random_country.population, np.array([individual]))
376
+ random_country.sort_population()
377
+ self.countries = sorted(self.countries, key=attrgetter('best_function'))
378
+ if not self.countries:
379
+ break
380
+ result = self.countries[0].population[0]
381
+
382
+ if self.printing:
383
+ print(f"{ti}) Лучшее решение: {result.real_x} - {result.f}, Стран осталось: {len(self.countries)}, Движение/Обмен/Войны/Эпидемии: {motion}/{trade}/{war}/{epedemic}")
384
+ print(f"Общее количество особей: {sum([len(country.population) for country in self.countries])}")
385
+ print("++++++++++++++++++++++++++++++++++++++++++++++++++")
386
+ for i, country in enumerate(self.countries):
387
+ print(f'{i + 1})', country.name, len(country.population), country.best_function, country.avg_function)
388
+ print("++++++++++++++++++++++++++++++++++++++++++++++++++")
389
+
390
+ if self.memory_list is not None:
391
+ self.memory_list[0] = ti
392
+ for i in range(len(result.real_x)):
393
+ self.memory_list[i + 1] = float(result.real_x[i])
394
+ self.memory_list[-1] = float(result.f)
395
+ return (result.real_x, result.f, False, ti)
396
+
397
+
398
+
399
+ # def f(x):
400
+ # return sum([(xi ** 4 - 16 * xi ** 2 + 5 *xi) / 2 for xi in x])
401
+ # #
402
+ # # k = 0
403
+ # # for i in range(100):
404
+ # CA = CountriesAlgorithm(
405
+ # f=f,
406
+ # Xmin=[-5.12 for i in range(3)],
407
+ # Xmax=[5.12 for i in range(3)],
408
+ # genes=[16 for i in range(3)],
409
+ # M=20,
410
+ # N=15,
411
+ # n=[1, 10],
412
+ # m=[3, 8],
413
+ # k=8,
414
+ # l=3,
415
+ # ep=[0.2, 0.4],
416
+ # max_mutation=16,
417
+ # tmax=300,
418
+ # printing=True,
419
+ # )
420
+ # r = CA.start()
421
+
422
+ # print(i, r[2], r[0], r[1])
423
+ # if r[2]:
424
+ # k += 1
425
+ #
426
+ # print(k/100)
@@ -0,0 +1,130 @@
1
+ import graycode
2
+ import numpy as np
3
+ import copy
4
+
5
+ class Individual:
6
+
7
+ x_min = None
8
+ x_max = None
9
+ genes = None
10
+ function = None
11
+ gray_code = None
12
+ f = None
13
+
14
+ def __init__(self, gray_code, x_min, x_max, genes, function, mutation_chance=None, max_mutation=1):
15
+
16
+ self.x_min = x_min
17
+ self.x_max = x_max
18
+ self.genes = genes
19
+ self.function = function
20
+ self.steps = (self.x_max - self.x_min) / (2 ** (self.genes) - 1)
21
+ self.gray_code = gray_code
22
+ if mutation_chance is not None and np.random.random() < mutation_chance:
23
+ self.mutation(max_mutation)
24
+ self.f = self.function(self.real_x)
25
+
26
+ @property
27
+ def real_x(self):
28
+ decimal_x = []
29
+ gray_code = copy.deepcopy(self.gray_code)
30
+ for g in self.genes:
31
+ decimal_x.append(graycode.gray_code_to_tc(int(gray_code[:g], base=2)))
32
+ gray_code = gray_code[g:]
33
+ return self.x_min + self.steps * np.array(decimal_x)
34
+
35
+ @property
36
+ def decimal_x(self):
37
+ return (self.real_x - self.x_min) / self.steps
38
+
39
+ @classmethod
40
+ def generate_from_decimal(cls, decimal, x_min, x_max, genes, function):
41
+ gray_code = ''
42
+ decimal = np.clip(decimal, np.zeros(decimal.size), 2 ** (genes) - 1)
43
+ for i in range(len(decimal)):
44
+ s = '{:0' + str(genes[i]) + 'b}'
45
+ gray_code += s.format(graycode.tc_to_gray_code(int(decimal[i])))
46
+
47
+ return cls(gray_code, x_min, x_max, genes, function)
48
+
49
+ @classmethod
50
+ def crossover(cls, individual1, individual2, mutation_chance, max_mutation=1):
51
+ k = np.random.randint(1, len(individual1.gray_code) - 1, 2)
52
+ while k[0] == k[1]:
53
+ k = np.random.randint(1, len(individual1.gray_code) - 1, 2)
54
+ k = np.sort(k)
55
+ new_gray1 = individual1.gray_code[:k[0]] + individual2.gray_code[k[0]:k[1]] + individual1.gray_code[k[1]:]
56
+ new_gray2 = individual2.gray_code[:k[0]] + individual1.gray_code[k[0]:k[1]] + individual2.gray_code[k[1]:]
57
+ return [
58
+ cls(new_gray1, individual1.x_min, individual1.x_max, individual1.genes,
59
+ individual1.function, mutation_chance, max_mutation),
60
+ cls(new_gray2, individual1.x_min, individual1.x_max, individual1.genes,
61
+ individual1.function, mutation_chance, max_mutation),
62
+ ]
63
+
64
+ def mutation(self, max_mutation=1):
65
+ if max_mutation > 0:
66
+ n = 1 + np.random.randint(1, max_mutation)
67
+ else:
68
+ n = 1
69
+ k = np.random.choice(len(self.gray_code), n, replace=False)
70
+ for ki in k:
71
+ b = bool(int(self.gray_code[ki]))
72
+ b = not b
73
+ b = str(int(b))
74
+ self.gray_code = self.gray_code[:ki] + b + self.gray_code[ki+1:]
75
+
76
+ def __lt__(self, other):
77
+ return self.f < other.f
78
+
79
+ def __le__(self, other):
80
+ return self.f <= other.f
81
+
82
+ def __gt__(self, other):
83
+ return self.f > other.f
84
+
85
+ def __ge__(self, other):
86
+ return self.f >= other.f
87
+
88
+
89
+ class GeneticAlgorithm:
90
+
91
+ def __init__(self, f, n, child_percent, mutation_chance, max_mutation, x_min, x_max, genes, t_max, printing=False):
92
+ self.f = f
93
+ self.n = n
94
+ self.child_percent = child_percent
95
+ self.mutation_chance = mutation_chance
96
+ self.max_mutation = max_mutation
97
+ self.x_min = np.array(x_min)
98
+ self.x_max = np.array(x_max)
99
+ self.genes = np.array(genes)
100
+ self.t_max = np.array(t_max)
101
+ self.printing = printing
102
+
103
+ self.rand_n_individual = np.vectorize(lambda x: x * self.random_individual(), signature='()->(n)')
104
+ self.generate_population = np.vectorize(lambda decimal: Individual.generate_from_decimal(
105
+ decimal, self.x_min, self.x_max, self.genes, self.f), signature='(n)->()')
106
+
107
+ def random_individual(self):
108
+ return np.random.randint(np.zeros(self.genes.size), 2 ** self.genes)
109
+
110
+ def start(self):
111
+ x = self.rand_n_individual(np.ones(self.n))
112
+ population = self.generate_population(x)
113
+ child_number = int(self.child_percent * self.n)
114
+
115
+ t = 0
116
+ while t <= self.t_max:
117
+ new_population = []
118
+ for i in range(child_number):
119
+ k = np.random.randint(0, self.n, 2)
120
+ while k[0] == k[1]:
121
+ k = np.random.randint(0, self.n, 2)
122
+ new_population += Individual.crossover(population[k[0]], population[k[1]],
123
+ self.mutation_chance, self.max_mutation)
124
+ population = np.append(population, np.array(new_population))
125
+ population.sort()
126
+ population = population[:self.n]
127
+ if self.printing:
128
+ print("Поколение {}: {} {}".format(t, population[0].real_x, population[0].f))
129
+ t += 1
130
+ return population[0].real_x
@@ -0,0 +1,127 @@
1
+ import numpy as np
2
+
3
+
4
+ class GoldDigger:
5
+
6
+ def __init__(self, x, function):
7
+ self.x = x
8
+ self.f = function(self.x)
9
+ self.ep_n = 0
10
+
11
+ def __lt__(self, other):
12
+ return self.f < other.f
13
+
14
+ def __le__(self, other):
15
+ return self.f <= other.f
16
+
17
+ def __gt__(self, other):
18
+ return self.f > other.f
19
+
20
+ def __ge__(self, other):
21
+ return self.f >= other.f
22
+
23
+ def __add__(self, other):
24
+ return self.f + other.f
25
+
26
+ def __radd__(self, other):
27
+ return self.f + other
28
+
29
+ def __truediv__(self, other):
30
+ return self.f / other
31
+
32
+ def update_function(self, function):
33
+ self.f = function(self.x)
34
+
35
+ def new_sigma_digger(self, x_min, x_max, sigma, function):
36
+ new_x = np.array([self.x[i] + np.random.normal(0, (x_max[i] - x_min[i]) * sigma) for i in range(self.x.size)])
37
+ new_x = np.clip(new_x, x_min, x_max)
38
+ return GoldDigger(new_x, function)
39
+
40
+
41
+
42
+ class GoldDiggersAlgorithm:
43
+
44
+ def __init__(self, f, n, k, l, u, a, b, sigma_b, sigma_e, Xmin, Xmax, m, t_max):
45
+ self.f = f
46
+ self.n = n
47
+ self.k = k
48
+ self.l = l
49
+ self.u = u
50
+ self.a = a
51
+ self.b = b
52
+ self.sigma_b = sigma_b
53
+ self.sigma_e = sigma_e
54
+ self.Xmin = np.array(Xmin)
55
+ self.Xmax = np.array(Xmax)
56
+ self.m = m
57
+ self.t_max = t_max
58
+ self.rand_mat = np.vectorize(lambda x: self.random_matrix(x, Xmin, Xmax), signature='()->(n)')
59
+ self.digger_init = np.vectorize(lambda x: GoldDigger(x, self.f), signature='(n)->()')
60
+
61
+ @staticmethod
62
+ def random_matrix(x, x_min, x_max):
63
+ return x * np.random.uniform(x_min, x_max)
64
+
65
+ def start(self):
66
+ x = self.rand_mat(np.ones(self.n))
67
+ population = self.digger_init(x)
68
+
69
+ t = 0
70
+ intervals = []
71
+ while t <= self.t_max:
72
+
73
+ x = self.rand_mat(np.ones(self.n))
74
+ in_interval = np.array([self.interval_in(xi, intervals) for xi in x])
75
+ if np.any(in_interval == True):
76
+ ind = np.where(in_interval == False)
77
+ new_x = x[ind]
78
+ if new_x.size:
79
+ population = np.append(population, self.digger_init(new_x))
80
+ ind = np.where(in_interval == True)
81
+ r = np.random.rand(ind[0].size)
82
+ rand_ind = np.where(r <= self.a)
83
+ ind = (ind[0][rand_ind])
84
+ x = x[ind]
85
+ if x.size:
86
+ population = np.append(population, self.digger_init(x))
87
+ else:
88
+ population = np.append(population, self.digger_init(x))
89
+
90
+ sigma = (((self.t_max - t) / self.t_max) ** self.m) * (self.sigma_b - self.sigma_e) + self.sigma_e
91
+
92
+ new_diggers = []
93
+ for digger in population:
94
+ for _ in range(self.k):
95
+ new_diggers.append(digger.new_sigma_digger(self.Xmin, self.Xmax, sigma, self.f))
96
+ population = np.append(population, new_diggers)
97
+ population = np.sort(population)
98
+
99
+ worst_diggers = population[self.n:]
100
+ r = np.random.rand(worst_diggers.size)
101
+ ind = np.where(r <= self.b)
102
+ worst_diggers = worst_diggers[ind]
103
+ for digger in worst_diggers:
104
+ intervals.append(
105
+ (digger.x - (self.Xmax - self.Xmin) * sigma, digger.x + (self.Xmax - self.Xmin) * sigma)
106
+ )
107
+ if len(intervals) > self.u:
108
+ intervals = intervals[len(intervals) - self.u - 1:len(intervals) - 1]
109
+ population = population[:self.n]
110
+ print("Поколение {}: {} {}".format(t, population[0].x, population[0].f))
111
+ t += 1
112
+ return population[0].x
113
+
114
+ @staticmethod
115
+ def interval_in(x, intervals):
116
+ for interval in intervals:
117
+ res = [x[i] >= interval[0][i] and x[i] <= interval[1][i] for i in range(len(x))]
118
+ if any(res):
119
+ return True
120
+ return False
121
+
122
+
123
+ def f(x):
124
+ return sum([(xi ** 4 - 16 * xi ** 2 + 5 *xi) / 2 for xi in x])
125
+
126
+ # gda = GoldDiggersAlgorithm(f, 15, 10, 10, 50, 0.5, 0.5, 0.5, 0.000001, [-5.12, -5.12, -5.12, -5.12, -5.12, -5.12, -5.12, -5.12, -5.12, -5.12], [5.12, 5.12, 5.12, 5.12, 5.12, 5.12, 5.12, 5.12, 5.12, 5.12], 2, 300)
127
+ # gda.start()
@@ -6,6 +6,7 @@ from scipy.integrate import simps
6
6
  from scipy.optimize import minimize
7
7
  from .country_optimization import CountriesAlgorithm
8
8
  from .country_optimization_v2 import CountriesAlgorithm_v2
9
+ from .genetic_optimization import GeneticAlgorithm
9
10
  from numba import njit
10
11
  import matplotlib.pyplot as plt
11
12
 
@@ -216,7 +217,8 @@ class BaseCompartmentModel:
216
217
  self.c0 = np.array(c0)
217
218
  self.w = np.ones(self.teoretic_y.shape) if w is None else np.array(w)
218
219
 
219
- def optimize(self, method=None, max_step=0.01, metric='R2', **kwargs):
220
+ def optimize(self, method=None, user_method=None, method_is_func=True,
221
+ optimization_func_name='__call__', max_step=0.01, metric='R2', **kwargs):
220
222
  """
221
223
  Функция оптимизации модели
222
224
 
@@ -230,28 +232,41 @@ class BaseCompartmentModel:
230
232
  """
231
233
  self._optim = True
232
234
  f = lambda x: self._target_function(x, max_step=max_step, metric=metric)
233
- if method == 'country_optimization':
234
- CA = CountriesAlgorithm(
235
- f=f,
236
- memory_list=getattr(self, 'memory', None),
237
- **kwargs
238
- )
239
- CA.start()
240
- x = CA.countries[0].population[0].x
241
- elif method == 'country_optimization_v2':
242
- CA = CountriesAlgorithm_v2(
243
- f=f,
244
- **kwargs
245
- )
246
- CA.start()
247
- x = CA.countries[0].population[0].x
235
+ if user_method is not None:
236
+ if method_is_func:
237
+ x = user_method(f, **kwargs)
238
+ else:
239
+ optimization_obj = user_method(f, **kwargs)
240
+ x = getattr(optimization_obj, optimization_func_name)()
248
241
  else:
249
- res = minimize(
250
- fun=f,
251
- method=method,
252
- **kwargs
253
- )
254
- x = res.x
242
+ if method == 'country_optimization':
243
+ CA = CountriesAlgorithm(
244
+ f=f,
245
+ memory_list=getattr(self, 'memory', None),
246
+ **kwargs
247
+ )
248
+ CA.start()
249
+ x = CA.countries[0].population[0].x
250
+ elif method == 'country_optimization_v2':
251
+ CA = CountriesAlgorithm_v2(
252
+ f=f,
253
+ **kwargs
254
+ )
255
+ CA.start()
256
+ x = CA.countries[0].population[0].x
257
+ elif method == 'GA':
258
+ CA = GeneticAlgorithm(
259
+ f=f,
260
+ **kwargs
261
+ )
262
+ x = CA.start()
263
+ else:
264
+ res = minimize(
265
+ fun=f,
266
+ method=method,
267
+ **kwargs
268
+ )
269
+ x = res.x
255
270
  if self.configuration_matrix_target:
256
271
  self.configuration_matrix[self.configuration_matrix_target] = x[:self.configuration_matrix_target_count]
257
272
  if self.outputs_target:
@@ -326,8 +341,9 @@ class MagicCompartmentModel(BaseCompartmentModel):
326
341
  if self.need_magic_optimization:
327
342
  self.magic_coefficient = x[-1]
328
343
 
329
- def optimize(self, method=None, max_step=0.01, **kwargs):
330
- x = super().optimize(method, max_step, **kwargs)
344
+ def optimize(self, method=None, user_method=None, method_is_func=True,
345
+ optimization_func_name='__call__', max_step=0.01, **kwargs):
346
+ x = super().optimize(method, user_method, method_is_func, optimization_func_name, max_step, **kwargs)
331
347
  if self.need_magic_optimization:
332
348
  self.magic_coefficient = x[-1]
333
349
  self.need_magic_optimization = False
@@ -592,8 +608,9 @@ class ReleaseCompartmentModel(BaseCompartmentModel):
592
608
  self.c0 = np.array(c0)
593
609
  self.w = np.ones(self.teoretic_y.shape) if w is None else np.array(w)
594
610
 
595
- def optimize(self, method=None, max_step=0.01, **kwargs):
596
- x = super().optimize(method, max_step, **kwargs)
611
+ def optimize(self, method=None, user_method=None, method_is_func=True,
612
+ optimization_func_name='__call__', max_step=0.01, **kwargs):
613
+ x = super().optimize(method, user_method, method_is_func, optimization_func_name, max_step, **kwargs)
597
614
  s = self.configuration_matrix_target_count + self.outputs_target_count + self.volumes_target_count
598
615
  if self.release_parameters_target:
599
616
  self.release_parameters[self.release_parameters_target] = x[s:s + self.release_parameters_target_count]
@@ -123,6 +123,75 @@ model.optimize(
123
123
  При оптимизации, вектор неизвестных это
124
124
  x = [configuration_matrix (неизвестные), outputs(неизвестные), volumes(неизвестные)]
125
125
 
126
+ Кроме того, вы можете использовать генетический алгоритм:
127
+ ```python
128
+ model.optimize(
129
+ method='GA',
130
+ x_min=[0.00001, 0.001, 0.01, 1, 1],
131
+ x_max=[1, 2, 1, 10, 3],
132
+ genes=[16, 17, 16, 20, 16],
133
+ n=100,
134
+ child_percent=0.3,
135
+ mutation_chance=0.5,
136
+ max_mutation=5,
137
+ t_max=300,
138
+ max_step=0.5,
139
+ printing=True,
140
+ )
141
+ ```
142
+
143
+ Вы даже можете использовать свой собственный алгоритм, если это необходимо
144
+
145
+ ```python
146
+ # CountriesAlgorithm - ваш класс алгоритма
147
+ # start - функция запуска алгоритма
148
+ # важно, чтобы ваша функция запуска возвращала numpy.array
149
+
150
+ model.optimize(
151
+ user_method=CountriesAlgorithm,
152
+ method_is_func=False,
153
+ optimization_func_name='start',
154
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], #ваши настроечные параметры
155
+ Xmax=[1, 2, 1, 10, 3],
156
+ genes=[16, 17, 16, 20, 16],
157
+ M=20,
158
+ N=25,
159
+ n=[1, 10],
160
+ max_mutation=8,
161
+ m=[1, 8],
162
+ k=8,
163
+ l=3,
164
+ ep=[0.2, 0.4],
165
+ tmax=200,
166
+ max_step=0.5,
167
+ printing=True
168
+ )
169
+ ```
170
+
171
+ или
172
+
173
+ ```python
174
+ # my_alg - ваша функция алгоритма, важно, чтобы она принимала только целевую функцию
175
+
176
+ model.optimize(
177
+ user_method=my_alg,
178
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], #ваши настроечные параметры
179
+ Xmax=[1, 2, 1, 10, 3],
180
+ genes=[16, 17, 16, 20, 16],
181
+ M=20,
182
+ N=25,
183
+ n=[1, 10],
184
+ max_mutation=8,
185
+ m=[1, 8],
186
+ k=8,
187
+ l=3,
188
+ ep=[0.2, 0.4],
189
+ tmax=200,
190
+ max_step=0.5,
191
+ printing=True
192
+ )
193
+ ```
194
+
126
195
  **4) Модель MagicCompartmentModel**
127
196
 
128
197
  Данная модель необходима нам для тех случаев,
@@ -329,6 +398,77 @@ printing=True,
329
398
  When optimizing, the vector of unknowns is
330
399
  x = [configuration_matrix (unknown), outputs(unknown), volumes(unknown)]
331
400
 
401
+ In addition, you can use a genetic algorithm:
402
+
403
+ ```python
404
+
405
+ model.optimize(
406
+ method='GA',
407
+ x_min=[0.00001, 0.001, 0.01, 1, 1],
408
+ x_max=[1, 2, 1, 10, 3],
409
+ genes=[16, 17, 16, 20, 16],
410
+ n=100,
411
+ percentage of descendants=0.3,
412
+ the probability of mutation =0.5,
413
+ max_mutation=5,
414
+ t_max=300,
415
+ max_step=0.5,
416
+ print=True,
417
+ )
418
+ ```
419
+
420
+ You can even use your own algorithm if necessary.
421
+
422
+ ```python
423
+ # Countryalgorithm - your class is an algorithm
424
+ # start - start the algorithm
425
+ # it is important that your application aroused the interest of numpy.array
426
+
427
+ model.optimize(
428
+ user_method=country Countryalgorithm,
429
+ method_is_func=False,
430
+ optimization_func_name='start',
431
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], # your desktop settings
432
+ Xmax Max=[1, 2, 1, 10, 3],
433
+ genes=[16, 17, 16, 20, 16],
434
+ M=20,
435
+ N=25,
436
+ n=[1, 10],
437
+ max_mutation=8,
438
+ m=[1, 8],
439
+ k=8,
440
+ l=3,
441
+ ep=[0,2, 0,4],
442
+ tmax=200,
443
+ max_step=0.5,
444
+ print=True
445
+ )
446
+ ```
447
+
448
+ or
449
+
450
+ ```python
451
+ # my_alg is your algorithm function, it is important that it accepts only the target function
452
+
453
+ model.optimize(
454
+ custom method=my_alg,
455
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], # your desktop settings
456
+ Xmax Max=[1, 2, 1, 10, 3],
457
+ genes=[16, 17, 16, 20, 16],
458
+ M=20,
459
+ N=25,
460
+ n=[1, 10],
461
+ max_mutation=8,
462
+ m=[1, 8],
463
+ k=8,
464
+ l=3,
465
+ ep=[0,2, 0,4],
466
+ tmax=200,
467
+ max_step=0.5,
468
+ print=True
469
+ )
470
+ ```
471
+
332
472
  **4) The MagicCompartmentModel model**
333
473
 
334
474
  We need this model for those cases
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: pypharm
3
- Version: 1.3.3
3
+ Version: 1.3.5
4
4
  Summary: Module for solving pharmacokinetic problems
5
5
  Home-page: https://github.com/Krash13/PyPharm
6
6
  Author: Krash13
@@ -139,6 +139,75 @@ model.optimize(
139
139
  При оптимизации, вектор неизвестных это
140
140
  x = [configuration_matrix (неизвестные), outputs(неизвестные), volumes(неизвестные)]
141
141
 
142
+ Кроме того, вы можете использовать генетический алгоритм:
143
+ ```python
144
+ model.optimize(
145
+ method='GA',
146
+ x_min=[0.00001, 0.001, 0.01, 1, 1],
147
+ x_max=[1, 2, 1, 10, 3],
148
+ genes=[16, 17, 16, 20, 16],
149
+ n=100,
150
+ child_percent=0.3,
151
+ mutation_chance=0.5,
152
+ max_mutation=5,
153
+ t_max=300,
154
+ max_step=0.5,
155
+ printing=True,
156
+ )
157
+ ```
158
+
159
+ Вы даже можете использовать свой собственный алгоритм, если это необходимо
160
+
161
+ ```python
162
+ # CountriesAlgorithm - ваш класс алгоритма
163
+ # start - функция запуска алгоритма
164
+ # важно, чтобы ваша функция запуска возвращала numpy.array
165
+
166
+ model.optimize(
167
+ user_method=CountriesAlgorithm,
168
+ method_is_func=False,
169
+ optimization_func_name='start',
170
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], #ваши настроечные параметры
171
+ Xmax=[1, 2, 1, 10, 3],
172
+ genes=[16, 17, 16, 20, 16],
173
+ M=20,
174
+ N=25,
175
+ n=[1, 10],
176
+ max_mutation=8,
177
+ m=[1, 8],
178
+ k=8,
179
+ l=3,
180
+ ep=[0.2, 0.4],
181
+ tmax=200,
182
+ max_step=0.5,
183
+ printing=True
184
+ )
185
+ ```
186
+
187
+ или
188
+
189
+ ```python
190
+ # my_alg - ваша функция алгоритма, важно, чтобы она принимала только целевую функцию
191
+
192
+ model.optimize(
193
+ user_method=my_alg,
194
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], #ваши настроечные параметры
195
+ Xmax=[1, 2, 1, 10, 3],
196
+ genes=[16, 17, 16, 20, 16],
197
+ M=20,
198
+ N=25,
199
+ n=[1, 10],
200
+ max_mutation=8,
201
+ m=[1, 8],
202
+ k=8,
203
+ l=3,
204
+ ep=[0.2, 0.4],
205
+ tmax=200,
206
+ max_step=0.5,
207
+ printing=True
208
+ )
209
+ ```
210
+
142
211
  **4) Модель MagicCompartmentModel**
143
212
 
144
213
  Данная модель необходима нам для тех случаев,
@@ -345,6 +414,77 @@ printing=True,
345
414
  When optimizing, the vector of unknowns is
346
415
  x = [configuration_matrix (unknown), outputs(unknown), volumes(unknown)]
347
416
 
417
+ In addition, you can use a genetic algorithm:
418
+
419
+ ```python
420
+
421
+ model.optimize(
422
+ method='GA',
423
+ x_min=[0.00001, 0.001, 0.01, 1, 1],
424
+ x_max=[1, 2, 1, 10, 3],
425
+ genes=[16, 17, 16, 20, 16],
426
+ n=100,
427
+ percentage of descendants=0.3,
428
+ the probability of mutation =0.5,
429
+ max_mutation=5,
430
+ t_max=300,
431
+ max_step=0.5,
432
+ print=True,
433
+ )
434
+ ```
435
+
436
+ You can even use your own algorithm if necessary.
437
+
438
+ ```python
439
+ # Countryalgorithm - your class is an algorithm
440
+ # start - start the algorithm
441
+ # it is important that your application aroused the interest of numpy.array
442
+
443
+ model.optimize(
444
+ user_method=country Countryalgorithm,
445
+ method_is_func=False,
446
+ optimization_func_name='start',
447
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], # your desktop settings
448
+ Xmax Max=[1, 2, 1, 10, 3],
449
+ genes=[16, 17, 16, 20, 16],
450
+ M=20,
451
+ N=25,
452
+ n=[1, 10],
453
+ max_mutation=8,
454
+ m=[1, 8],
455
+ k=8,
456
+ l=3,
457
+ ep=[0,2, 0,4],
458
+ tmax=200,
459
+ max_step=0.5,
460
+ print=True
461
+ )
462
+ ```
463
+
464
+ or
465
+
466
+ ```python
467
+ # my_alg is your algorithm function, it is important that it accepts only the target function
468
+
469
+ model.optimize(
470
+ custom method=my_alg,
471
+ Xmin=[0.00001, 0.001, 0.01, 1, 1], # your desktop settings
472
+ Xmax Max=[1, 2, 1, 10, 3],
473
+ genes=[16, 17, 16, 20, 16],
474
+ M=20,
475
+ N=25,
476
+ n=[1, 10],
477
+ max_mutation=8,
478
+ m=[1, 8],
479
+ k=8,
480
+ l=3,
481
+ ep=[0,2, 0,4],
482
+ tmax=200,
483
+ max_step=0.5,
484
+ print=True
485
+ )
486
+ ```
487
+
348
488
  **4) The MagicCompartmentModel model**
349
489
 
350
490
  We need this model for those cases
@@ -4,6 +4,9 @@ setup.py
4
4
  PyPharm/__init__.py
5
5
  PyPharm/country_optimization.py
6
6
  PyPharm/country_optimization_v2.py
7
+ PyPharm/country_optimization_v3.py
8
+ PyPharm/genetic_optimization.py
9
+ PyPharm/gold_digger_optimization.py
7
10
  PyPharm/models.py
8
11
  pypharm.egg-info/PKG-INFO
9
12
  pypharm.egg-info/SOURCES.txt
@@ -6,7 +6,7 @@ def readme():
6
6
 
7
7
  setup(
8
8
  name='pypharm',
9
- version='1.3.3',
9
+ version='1.3.5',
10
10
  author='Krash13',
11
11
  author_email='krasheninnikov.r.s@muctr.ru',
12
12
  description='Module for solving pharmacokinetic problems',
@@ -14,7 +14,7 @@ setup(
14
14
  long_description_content_type='text/markdown',
15
15
  url='https://github.com/Krash13/PyPharm',
16
16
  packages=find_packages(),
17
- install_requires=['numpy>=1.22.1', 'scipy>=1.8.0', 'numba>=0.58.1', 'matplotlib>=3.5.1 '],
17
+ install_requires=['numpy>=1.22.1', 'scipy>=1.8.0', 'numba>=0.58.1', 'matplotlib>=3.5.1'],
18
18
  classifiers=[
19
19
  'Programming Language :: Python :: 3.9',
20
20
  'License :: OSI Approved :: BSD License',
File without changes
File without changes