Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 8cbb307

Browse files
Update docs and NSGA edits
1 parent 655fd15 commit 8cbb307

File tree

8 files changed

+2506
-2312
lines changed

8 files changed

+2506
-2312
lines changed

‎docs/source/helper.rst‎

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,5 +7,23 @@ This section of the PyGAD's library documentation discusses the
77
**pygad.helper** module.
88

99
Yet, this module has a submodule called ``unique`` that has a class
10-
named ``Unique`` with some helper methods. Such methods help to check
11-
and fix duplicate values in the genes of a solution.
10+
named ``Unique`` with the following helper methods. Such methods help to
11+
check and fix duplicate values in the genes of a solution.
12+
13+
- ``solve_duplicate_genes_randomly()``: Solves the duplicates in a
14+
solution by randomly selecting new values for the duplicating genes.
15+
16+
- ``solve_duplicate_genes_by_space()``: Solves the duplicates in a
17+
solution by selecting values for the duplicating genes from the gene
18+
space
19+
20+
- ``unique_int_gene_from_range()``: Finds a unique integer value for
21+
the gene.
22+
23+
- ``unique_genes_by_space()``: Loops through all the duplicating genes
24+
to find unique values that from their gene spaces to solve the
25+
duplicates. For each duplicating gene, a call to the
26+
``unique_gene_by_space()`` is made.
27+
28+
- ``unique_gene_by_space()``: Returns a unique gene value for a single
29+
gene based on its value space to solve the duplicates.

‎docs/source/pygad.rst‎

Lines changed: 104 additions & 101 deletions
Original file line numberDiff line numberDiff line change
@@ -595,24 +595,6 @@ Other Methods
595595
- ``adaptive_mutation_population_fitness()``: Returns the average
596596
fitness value used in the adaptive mutation to filter the solutions.
597597

598-
- ``solve_duplicate_genes_randomly()``: Solves the duplicates in a
599-
solution by randomly selecting new values for the duplicating genes.
600-
601-
- ``solve_duplicate_genes_by_space()``: Solves the duplicates in a
602-
solution by selecting values for the duplicating genes from the gene
603-
space
604-
605-
- ``unique_int_gene_from_range()``: Finds a unique integer value for
606-
the gene.
607-
608-
- ``unique_genes_by_space()``: Loops through all the duplicating genes
609-
to find unique values that from their gene spaces to solve the
610-
duplicates. For each duplicating gene, a call to the
611-
``unique_gene_by_space()`` is made.
612-
613-
- ``unique_gene_by_space()``: Returns a unique gene value for a single
614-
gene based on its value space to solve the duplicates.
615-
616598
- ``summary()``: Prints a Keras-like summary of the PyGAD lifecycle.
617599
This helps to have an overview of the architecture. Supported in
618600
`PyGAD
@@ -961,31 +943,6 @@ generation.
961943
It works only after completing at least 1 generation. If no generation
962944
is completed (at least 1), an exception is raised.
963945

964-
This method accepts the following parameters:
965-
966-
1. ``title``: Title of the figure.
967-
968-
2. ``xlabel``: X-axis label.
969-
970-
3. ``ylabel``: Y-axis label.
971-
972-
4. ``linewidth``: Line width of the plot. Defaults to ``3``.
973-
974-
5. ``font_size``: Font size for the labels and title. Defaults to
975-
``14``.
976-
977-
6. ``plot_type``: Type of the plot which can be either ``"plot"``
978-
(default), ``"scatter"``, or ``"bar"``.
979-
980-
7. ``color``: Color of the plot which defaults to the greenish color
981-
``"#64f20c"``.
982-
983-
8. ``label``: The label used for the legend in the figures of
984-
multi-objective problems. It is not used for single-objective
985-
problems. It defaults to ``None`` which means no labels used.
986-
987-
9. ``save_dir``: Directory to save the figure.
988-
989946
.. _plotnewsolutionrate:
990947

991948
``plot_new_solution_rate()``
@@ -999,26 +956,6 @@ constructor of the ``pygad.GA`` class.
999956
It works only after completing at least 1 generation. If no generation
1000957
is completed (at least 1), an exception is raised.
1001958

1002-
This method accepts the following parameters:
1003-
1004-
1. ``title``: Title of the figure.
1005-
1006-
2. ``xlabel``: X-axis label.
1007-
1008-
3. ``ylabel``: Y-axis label.
1009-
1010-
4. ``linewidth``: Line width of the plot. Defaults to ``3``.
1011-
1012-
5. ``font_size``: Font size for the labels and title. Defaults to
1013-
``14``.
1014-
1015-
6. ``plot_type``: Type of the plot which can be either ``"plot"``
1016-
(default), ``"scatter"``, or ``"bar"``.
1017-
1018-
7. ``color``: Color of the plot which defaults to ``"#3870FF"``.
1019-
1020-
8. ``save_dir``: Directory to save the figure.
1021-
1022959
.. _plotgenes:
1023960

1024961
``plot_genes()``
@@ -1039,43 +976,6 @@ This is controlled by the ``graph_type`` parameter.
1039976
It works only after completing at least 1 generation. If no generation
1040977
is completed (at least 1), an exception is raised.
1041978

1042-
This method accepts the following parameters:
1043-
1044-
1. ``title``: Title of the figure.
1045-
1046-
2. ``xlabel``: X-axis label.
1047-
1048-
3. ``ylabel``: Y-axis label.
1049-
1050-
4. ``linewidth``: Line width of the plot. Defaults to ``3``.
1051-
1052-
5. ``font_size``: Font size for the labels and title. Defaults to
1053-
``14``.
1054-
1055-
6. ``plot_type``: Type of the plot which can be either ``"plot"``
1056-
(default), ``"scatter"``, or ``"bar"``.
1057-
1058-
7. ``graph_type``: Type of the graph which can be either ``"plot"``
1059-
(default), ``"boxplot"``, or ``"histogram"``.
1060-
1061-
8. ``fill_color``: Fill color of the graph which defaults to
1062-
``"#3870FF"``. This has no effect if ``graph_type="plot"``.
1063-
1064-
9. ``color``: Color of the plot which defaults to ``"#3870FF"``.
1065-
1066-
10. ``solutions``: Defaults to ``"all"`` which means use all solutions.
1067-
If ``"best"`` then only the best solutions are used.
1068-
1069-
11. ``save_dir``: Directory to save the figure.
1070-
1071-
An exception is raised if:
1072-
1073-
- ``solutions="all"`` while ``save_solutions=False`` in the constructor
1074-
of the ``pygad.GA`` class. .
1075-
1076-
- ``solutions="best"`` while ``save_best_solutions=False`` in the
1077-
constructor of the ``pygad.GA`` class. .
1078-
1079979
``save()``
1080980
----------
1081981

@@ -1160,7 +1060,8 @@ optimization problem is single-objective or multi-objective.
11601060
- If the fitness function returns a ``list``, ``tuple``, or
11611061
``numpy.ndarray``, then the problem is single-objective. Even if
11621062
there is only one element, the problem is still considered
1163-
multi-objective.
1063+
multi-objective. Each element represents the fitness value of its
1064+
corresponding objective.
11641065

11651066
Using a user-defined fitness function allows the user to freely use
11661067
PyGAD to solve any problem by passing the appropriate fitness
@@ -1580,6 +1481,108 @@ below.
15801481
loaded_ga_instance = pygad.load(filename=filename)
15811482
loaded_ga_instance.plot_fitness()
15821483
1484+
Linear Model Optimization - Multi-Objective
1485+
-------------------------------------------
1486+
1487+
This is a multi-objective optimization example that optimizes these 2
1488+
functions:
1489+
1490+
1. ``y1 = f(w1:w6) = w1x1 + w2x2 + w3x3 + w4x4 + w5x5 + 6wx6``
1491+
1492+
2. ``y2 = f(w1:w6) = w1x7 + w2x8 + w3x9 + w4x10 + w5x11 + 6wx12``
1493+
1494+
Where:
1495+
1496+
1. ``(x1,x2,x3,x4,x5,x6)=(4,-2,3.5,5,-11,-4.7)`` and ``y=50``
1497+
1498+
2. ``(x7,x8,x9,x10,x11,x12)=(-2,0.7,-9,1.4,3,5)`` and ``y=30``
1499+
1500+
The 2 functions use the same parameters (weights) ``w1`` to ``w6``.
1501+
1502+
The goal is to use PyGAD to find the optimal values for such weights
1503+
that satisfy the 2 functions ``y1`` and ``y2``.
1504+
1505+
To use PyGAD to solve multi-objective problems, the only adjustment is
1506+
to return a ``list``, ``tuple``, or ``numpy.ndarray`` from the fitness
1507+
function. Each element represents the fitness of an objective in order.
1508+
That is the first element is the fitness of the first objective, the
1509+
second element is the fitness for the second objective, and so on.
1510+
1511+
.. code:: python
1512+
1513+
import pygad
1514+
import numpy
1515+
1516+
"""
1517+
Given these 2 functions:
1518+
y1 = f(w1:w6) = w1x1 + w2x2 + w3x3 + w4x4 + w5x5 + 6wx6
1519+
y2 = f(w1:w6) = w1x7 + w2x8 + w3x9 + w4x10 + w5x11 + 6wx12
1520+
where (x1,x2,x3,x4,x5,x6)=(4,-2,3.5,5,-11,-4.7) and y=50
1521+
and (x7,x8,x9,x10,x11,x12)=(-2,0.7,-9,1.4,3,5) and y=30
1522+
What are the best values for the 6 weights (w1 to w6)? We are going to use the genetic algorithm to optimize these 2 functions.
1523+
This is a multi-objective optimization problem.
1524+
1525+
PyGAD considers the problem as multi-objective if the fitness function returns:
1526+
1) List.
1527+
2) Or tuple.
1528+
3) Or numpy.ndarray.
1529+
"""
1530+
1531+
function_inputs1 = [4,-2,3.5,5,-11,-4.7] # Function 1 inputs.
1532+
function_inputs2 = [-2,0.7,-9,1.4,3,5] # Function 2 inputs.
1533+
desired_output1 = 50 # Function 1 output.
1534+
desired_output2 = 30 # Function 2 output.
1535+
1536+
def fitness_func(ga_instance, solution, solution_idx):
1537+
output1 = numpy.sum(solution*function_inputs1)
1538+
output2 = numpy.sum(solution*function_inputs2)
1539+
fitness1 = 1.0 / (numpy.abs(output1 - desired_output1) + 0.000001)
1540+
fitness2 = 1.0 / (numpy.abs(output2 - desired_output2) + 0.000001)
1541+
return [fitness1, fitness2]
1542+
1543+
num_generations = 100
1544+
num_parents_mating = 10
1545+
1546+
sol_per_pop = 20
1547+
num_genes = len(function_inputs1)
1548+
1549+
ga_instance = pygad.GA(num_generations=num_generations,
1550+
num_parents_mating=num_parents_mating,
1551+
sol_per_pop=sol_per_pop,
1552+
num_genes=num_genes,
1553+
fitness_func=fitness_func,
1554+
parent_selection_type='nsga2')
1555+
1556+
ga_instance.run()
1557+
1558+
ga_instance.plot_fitness(label=['Obj 1', 'Obj 2'])
1559+
1560+
solution, solution_fitness, solution_idx = ga_instance.best_solution(ga_instance.last_generation_fitness)
1561+
print(f"Parameters of the best solution : {solution}")
1562+
print(f"Fitness value of the best solution = {solution_fitness}")
1563+
1564+
prediction = numpy.sum(numpy.array(function_inputs1)*solution)
1565+
print(f"Predicted output 1 based on the best solution : {prediction}")
1566+
prediction = numpy.sum(numpy.array(function_inputs2)*solution)
1567+
print(f"Predicted output 2 based on the best solution : {prediction}")
1568+
1569+
This is the result of the print statements. The predicted outputs are
1570+
close to the desired outputs.
1571+
1572+
.. code::
1573+
1574+
Parameters of the best solution : [ 0.79676439 -2.98823386 -4.12677662 5.70539445 -2.02797016 -1.07243922]
1575+
Fitness value of the best solution = [ 1.68090829 349.8591915 ]
1576+
Predicted output 1 based on the best solution : 50.59491545442283
1577+
Predicted output 2 based on the best solution : 29.99714270722312
1578+
1579+
This is the figure created by the ``plot_fitness()`` method. The fitness
1580+
of the first objective has the green color. The blue color is used for
1581+
the second objective fitness.
1582+
1583+
.. image:: https://github.com/ahmedfgad/GeneticAlgorithmPython/assets/16560492/7896f8d8-01c5-4ff9-8d15-52191c309b63
1584+
:alt:
1585+
15831586
Reproducing Images
15841587
------------------
15851588

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /