Skip to content

Commit

Permalink
Refactor of scheduling for compatibility with multi-objective optimiz…
Browse files Browse the repository at this point in the history
…ation (#81)

 - Change the contract of schedulers schedule method. It now returns a list of schedules rather than just one schedule
 - Pipelines now also return a list of schedules
 - In the Genetic Algorithm, multicriteria is now a scheduler parameter, and the standard schedule method is used to obtain 
   schedules. This ensures compatibility of multi-objective scheduling with pipelines
  • Loading branch information
Timotshak authored Feb 14, 2024
1 parent 40e176e commit 0f3c198
Show file tree
Hide file tree
Showing 39 changed files with 15,026 additions and 14,727 deletions.
8 changes: 4 additions & 4 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -130,14 +130,14 @@ To use SAMPO for the schedule generation you need to prepare:
from sampo.scheduler.genetic import GeneticScheduler
scheduler = GeneticScheduler(mutate_order=0.1,
mutate_resources=0.3)
scheduler = GeneticScheduler(mutate_order=0.05,
mutate_resources=0.05)
2.2. Schedule generation

.. code-block:: python
schedule = scheduler.schedule(wg, contractors)
schedule = scheduler.schedule(wg, contractors)[0]
3. Pipeline structure

Expand All @@ -151,7 +151,7 @@ When data was prepared and scheduler built, you should use scheduling pipeline t
.wg(wg) \
.contractors(contractors) \
.schedule(HEFTScheduler()) \
.finish()
.finish()[0]
Supported by
============
Expand Down
8 changes: 4 additions & 4 deletions docs/source/Usage.rst
Original file line number Diff line number Diff line change
Expand Up @@ -72,14 +72,14 @@ To use SAMPO for the schedule generation you need to prepare:
from sampo.scheduler.genetic import GeneticScheduler
scheduler = GeneticScheduler(mutate_order=0.1,
mutate_resources=0.3)
scheduler = GeneticScheduler(mutate_order=0.05,
mutate_resources=0.05)
2.2. Schedule generation

.. code-block:: python
schedule = scheduler.schedule(wg, contractors)
schedule = scheduler.schedule(wg, contractors)[0]
3. Pipeline structure

Expand All @@ -93,4 +93,4 @@ When data was prepared and scheduler built, you should use scheduling pipeline t
.wg(wg) \
.contractors(contractors) \
.schedule(HEFTScheduler()) \
.finish()
.finish()[0]
2 changes: 1 addition & 1 deletion examples/field_development/field_development_scheduling.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@
start_date = "2023-01-01" # Set up the project's start date

# Schedule field development tasks
schedule = scheduler_type.schedule(structured_wg, contractors, validate=True)
schedule = scheduler_type.schedule(structured_wg, contractors, validate=True)[0]
schedule_df = schedule.merged_stages_datetime_df(start_date)

# Schedule's gant chart visualization
Expand Down
4 changes: 2 additions & 2 deletions examples/generator_scenarios.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
p_rand = SimpleSynthetic(rand=231)
wg = p_rand.work_graph(top_border=3000)
contractors = [p_rand.contractor(i) for i in range(10, 31, 10)]
schedule = HEFTScheduler().schedule(wg, contractors)
schedule = HEFTScheduler().schedule(wg, contractors)[0]

print(len(wg.nodes))
print("\nDefault contractors")
Expand All @@ -24,7 +24,7 @@
print("\nContractor by work graph")
for pack_counts in []:#[1, 2, 10]:
contractors = [get_contractor_by_wg(wg, scaler=pack_counts)]
execution_time = HEFTScheduler().schedule(wg, contractors).execution_time
execution_time = HEFTScheduler().schedule(wg, contractors)[0].execution_time
print(f"Execution time: {execution_time}, pack count: {pack_counts}")

print("\nNames extension")
Expand Down
175 changes: 107 additions & 68 deletions examples/local_optimization.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,13 @@
"cell_type": "code",
"execution_count": 1,
"metadata": {
"collapsed": true,
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.215669600Z",
"start_time": "2023-10-31T08:06:05.535679400Z"
},
"collapsed": true,
"jupyter": {
"outputs_hidden": true
}
},
"outputs": [],
Expand All @@ -21,16 +24,29 @@
},
{
"cell_type": "markdown",
"metadata": {
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"source": [
"# 1. Data preparation"
],
"metadata": {
"collapsed": false
}
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.275585700Z",
"start_time": "2023-10-31T08:06:06.215669600Z"
},
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"outputs": [],
"source": [
"# SimpleSynthetic object used for the simple work graph structure generation\n",
Expand All @@ -49,38 +65,47 @@
"contractors = [get_contractor_by_wg(simple_wg)]\n",
"\n",
"scheduler = HEFTScheduler()"
],
"metadata": {
"collapsed": false,
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.275585700Z",
"start_time": "2023-10-31T08:06:06.215669600Z"
}
}
]
},
{
"cell_type": "markdown",
"metadata": {
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"source": [
"# 2. Local optimization\n",
"There are two types of local optimization in SAMPO: order and schedule."
],
"metadata": {
"collapsed": false
}
]
},
{
"cell_type": "markdown",
"metadata": {
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"source": [
"### Scheduling order optimization\n",
"This local optimization should rearrange scheduling order to improve scheduling results."
],
"metadata": {
"collapsed": false
}
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.450877800Z",
"start_time": "2023-10-31T08:06:06.365998300Z"
},
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"outputs": [
{
"name": "stdout",
Expand All @@ -91,7 +116,9 @@
},
{
"data": {
"text/plain": "1194"
"text/plain": [
"1194"
]
},
"execution_count": 3,
"metadata": {},
Expand All @@ -108,35 +135,43 @@
" .contractors(contractors) \\\n",
" .optimize_local(local_optimizer, range(0, 10)) \\\n",
" .schedule(scheduler) \\\n",
" .finish()\n",
" .finish()[0]\n",
"\n",
"project.schedule.execution_time"
],
"metadata": {
"collapsed": false,
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.450877800Z",
"start_time": "2023-10-31T08:06:06.365998300Z"
}
}
]
},
{
"cell_type": "markdown",
"metadata": {
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"source": [
"### Schedule optimization\n",
"This local optimization should recalculate parts of schedule to make it better."
],
"metadata": {
"collapsed": false
}
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.635515100Z",
"start_time": "2023-10-31T08:06:06.465560600Z"
},
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"outputs": [
{
"data": {
"text/plain": "1194"
"text/plain": [
"1194"
]
},
"execution_count": 4,
"metadata": {},
Expand All @@ -154,32 +189,38 @@
" .contractors(contractors) \\\n",
" .schedule(scheduler) \\\n",
" .optimize_local(local_optimizer, range(0, 5)) \\\n",
" .finish()\n",
" .finish()[0]\n",
"\n",
"project.schedule.execution_time"
],
"metadata": {
"collapsed": false,
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.635515100Z",
"start_time": "2023-10-31T08:06:06.465560600Z"
}
}
]
},
{
"cell_type": "markdown",
"metadata": {
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"source": [
"### Both\n",
"Using pipeline you can apply both type of optimizations.\n",
"You also can stack local optimizers, they should be applied sequentially."
],
"metadata": {
"collapsed": false
}
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.860829700Z",
"start_time": "2023-10-31T08:06:06.690476Z"
},
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
},
"outputs": [
{
"name": "stdout",
Expand Down Expand Up @@ -306,7 +347,9 @@
},
{
"data": {
"text/plain": "1240"
"text/plain": [
"1240"
]
},
"execution_count": 5,
"metadata": {},
Expand All @@ -327,51 +370,47 @@
" .schedule(scheduler) \\\n",
" .optimize_local(schedule_optimizer, range(0, simple_wg.vertex_count // 2)) \\\n",
" .optimize_local(schedule_optimizer, range(simple_wg.vertex_count // 2, simple_wg.vertex_count)) \\\n",
" .finish()\n",
" .finish()[0]\n",
"\n",
"project.schedule.execution_time"
],
"metadata": {
"collapsed": false,
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.860829700Z",
"start_time": "2023-10-31T08:06:06.690476Z"
}
}
]
},
{
"cell_type": "code",
"execution_count": 5,
"outputs": [],
"source": [],
"metadata": {
"collapsed": false,
"ExecuteTime": {
"end_time": "2023-10-31T08:06:06.870912400Z",
"start_time": "2023-10-31T08:06:06.855820800Z"
},
"collapsed": false,
"jupyter": {
"outputs_hidden": false
}
}
},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"display_name": "Python 3 (ipykernel)",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 2
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython2",
"version": "2.7.6"
"pygments_lexer": "ipython3",
"version": "3.12.2"
}
},
"nbformat": 4,
"nbformat_minor": 0
"nbformat_minor": 4
}
Loading

0 comments on commit 0f3c198

Please sign in to comment.