Skip to content

A tool to perform optimization of ship routes based on fuel consumption in different weather conditions

Notifications You must be signed in to change notification settings

52North/WeatherRoutingTool

Repository files navigation

Weather Routing Tool (WRT)

Installation instructions

Steps:

  • clone the repository: git clone https://github.com/52North/WeatherRoutingTool.git
  • change to the folder: cd WeatherRoutingTool
  • [recommended] create and activate a virtual environment, e.g.
    • python3 -m venv "venv"
    • source venv/bin/activate
  • install the WRT: pip install . or in editable mode (recommended for development) pip install -e .

Power/fuel consumption framework

In order to get high-quality results, a suitable power/fuel modelling framework should be used as it is the core of any weather routing optimization.

The WRT was originally implemented within the research project MariData. Within this project the power/fuel modelling framework mariPower was developed by project partners from the Institute of Fluid Dynamics and Ship Theory of the Hamburg University of Technology. The mariPower package allows to predict engine power and fuel consumption under various environmental conditions for specific ships investigated in the project. More details about the package and the project as a whole can be found in the following publication: https://proceedings.open.tudelft.nl/imdc24/article/view/875.
The mariPower package is closed source software and this will most likely not change in the future. However, as power demand varies from ship to ship users have to provide code for making power predictions on their own suitable to the use case.

For users with access to mariPower:

  • clone the repository
  • change to the folder: cd maripower
  • install mariPower: pip install . or pip install -e .

For users without access to mariPower:

One way to quickly test the WRT without mariPower is to use the configuration ALGORITHM_TYPE='speedy_isobased' and specifying the config parameter 'CONSTANT_FUEL_RATE'. This will assume a constant fuel rate of the vessel in any condition (high waves, low waves, etc.) and at any time. Of course, results will be highly inaccurate, but it is a way to quickly try and test the code and get some first ideas of possible routes.

New ships with their own power/fuel model can be integrated by implementing a new ship class and using it in the config.

In the future, it would be interesting to integrate general empirical formulas for power demand which provide reasonable results based on a small set of general ship parameters provided by the user like length and draft of the ship. However, for optimal results it is necessary to have a power prediction framework specifically designed for the ship(s) investigated. This could be based, e.g., on physical laws or data driven.

Configure and run the tool

Configuration of the Weather Routing Tool can be done by providing a json file. An example is given by config.example.json.

The configuration file has to be provided when calling the Weather Routing Tool from the command line:

python3 WeatherRoutingTool/cli.py -f <path>/config.json

Additionally, it's possible to define files for logging (separately for info and warning level) and if debugging mode should be used. Check the help text to get an overview of all CLI arguments:

$ python WeatherRoutingTool/cli.py --help
usage: cli.py [-h] -f FILE [--warnings-log-file WARNINGS_LOG_FILE] [--info-log-file INFO_LOG_FILE] [--debug DEBUG] [--filter-warnings FILTER_WARNINGS]

Weather Routing Tool

options:
  -h, --help            show this help message and exit
  -f FILE, --file FILE  Config file name (absolute path)
  --warnings-log-file WARNINGS_LOG_FILE
                        Logging file name (absolute path) for warnings and above.
  --info-log-file INFO_LOG_FILE
                        Logging file name (absolute path) for info and above.
  --debug DEBUG         Enable debug mode. <True|False>. Defaults to 'False'.
  --filter-warnings FILTER_WARNINGS
                        Filter action. <default|error|ignore|always|module|once>.Defaults to 'default'.

Some variables have to be set using environment variables (see below).

Config file

The following lists contain information on each variable which can be set.

Required variables (no default values provided):

  • COURSES_FILE: path to file that acts as intermediate storage for courses per routing step
  • DEFAULT_MAP: bbox in which route optimization is performed (lat_min, lon_min, lat_max, lon_max)
  • DEFAULT_ROUTE: start and end point of the route (lat_start, lon_start, lat_end, lon_end)
  • DEPARTURE_TIME: start time of travelling, format: 'yyyy-mm-ddThh:mmZ'
  • DEPTH_DATA: path to depth data (Attention: if DATA_MODE is automatic or odc, this file will be overwritten!)
  • ROUTE_PATH: path to json file to which the route will be written
  • WEATHER_DATA: path to weather data (Attention: if DATA_MODE is automatic or odc, this file will be overwritten!)

Recommended variables (default values provided but might be inaccurate/unsuitable):

  • BOAT_DRAUGHT_AFT: aft draught (draught at rudder) in m
  • BOAT_DRAUGHT_FORE: fore draught (draught at forward perpendicular) in m
  • BOAT_ROUGHNESS_DISTRIBUTION_LEVEL: numeric value (default: 1)
  • BOAT_ROUGHNESS_LEVEL: numeric value (default: 1)
  • BOAT_SPEED: in m/s
  • DATA_MODE: options: 'automatic', 'from_file', 'odc'

Optional variables (default values provided and don't need to be changed normally):

  • ALGORITHM_TYPE: options: 'isofuel'
  • CONSTRAINTS_LIST: options: 'land_crossing_global_land_mask', 'land_crossing_polygons', 'seamarks', 'water_depth', 'on_map', 'via_waypoints', 'status_error'
  • DELTA_FUEL: amount of fuel per routing step (kg)
  • DELTA_TIME_FORECAST: time resolution of weather forecast (hours)
  • FACTOR_CALM_WATER: multiplication factor for the calm water resistance model
  • FACTOR_WAVE_FORCES: multiplication factor for the added resistance in waves model
  • FACTOR_WIND_FORCES: multiplication factor for the added resistance in wind model
  • GENETIC_MUTATION_TYPE: type for mutation (options: 'grid_based')
  • GENETIC_NUMBER_GENERATIONS: number of generations for genetic algorithm
  • GENETIC_NUMBER_OFFSPRINGS: number of offsprings for genetic algorithm
  • GENETIC_POPULATION_SIZE: population size for genetic algorithm
  • GENETIC_POPULATION_TYPE: type for initial population (options: 'grid_based', 'from_geojson')
  • INTERMEDIATE_WAYPOINTS: [[lat_one,lon_one], [lat_two,lon_two] ... ]
  • ISOCHRONE_MAX_ROUTING_STEPS: maximum number of routing steps. Applies also if more than one route is searched!
  • ISOCHRONE_MINIMISATION_CRITERION: options: 'dist', 'squareddist_over_disttodest'
  • ISOCHRONE_NUMBER_OF_ROUTES: integer specifying how many routes should be searched (default: 1)
  • ISOCHRONE_PRUNE_GROUPS: can be 'courses', 'larger_direction', 'branch'
  • ISOCHRONE_PRUNE_SECTOR_DEG_HALF: half of the angular range of azimuth angle considered for pruning; not used for branch-based pruning
  • ISOCHRONE_PRUNE_SEGMENTS: total number of azimuth bins used for pruning in prune sector; not used for branch-based pruning
  • ISOCHRONE_PRUNE_SYMMETRY_AXIS: symmetry axis for pruning. Can be 'gcr' or 'headings_based'; not used for branch-based pruning
  • ROUTER_HDGS_INCREMENTS_DEG: increment of headings
  • ROUTER_HDGS_SEGMENTS: total number of headings (put even number!!); headings are oriented around the great circle from current point to (temporary - i.e. next waypoint if used) destination
  • ROUTE_POSTPROCESSING: enable route postprocessing to follow the Traffic Separation Scheme in route postprocessing
  • SHIP_TYPE: options: 'CBT', 'SAL'
  • TIME_FORECAST: forecast hours weather

Environment variables

Credentials for the Copernicus Marine Environment Monitoring Service (CMEMS) to download weather/ocean data:

  • CMEMS_USERNAME
  • CMEMS_PASSWORD

If not provided DATA_MODE='automatic' cannot be used.

Configuration parameters for the database which stores OpenSeaMap data:

  • WRT_DB_HOST
  • WRT_DB_PORT
  • WRT_DB_DATABASE
  • WRT_DB_USERNAME
  • WRT_DB_PASSWORD

If not provided the 'land_crossing_polygons' and 'seamarks' options of CONSTRAINTS_LIST and ROUTE_POSTPROCESSING=True cannot be used.

Path for storing figures (mainly for debugging purposes):

  • WRT_FIGURE_PATH

If not set or the path doesn't exist or access rights are wrong, no figures will be saved.

You can define the environment variables in a separate .env file and call the provided shell script:

source <path-to-WRT>/load_wrt.sh

Logging and Debugging

All log messages are sent to stdout by default. In addition, info and warning logs can be saved separately to file. Debugging mode can be enabled (disabled by default) which sets the stream (stdout) logging level to debug.

The top-level logger is named "WRT". Child loggers are following the scheme "WRT.". They inherit the top-level loggers' logging level.

Input data

Depending on the power/fuel consumption model used, different sets of environmental data are needed. The data described below are needed for the usage of mariPower.

There are three general options on how to provide the necessary input data:

  1. The easiest option is to set the config parameter DATA_MODE='automatic'. To use it, valid CMEMS credentials have to be configured using system environment variables (see above). In this case, the WRT will automatically download the necessary weather and ocean data for the chosen temporal and spatial extent and store it in the file specified by the config variable WEATHER_DATA. Moreover, water depth data from NOAA is downloaded and stored in the file specified by the config variable DEPTH_DATA.

  2. It is also possible to prepare two NetCDF files containing the weather and ocean data and the water depth data and pointing the WRT to these files using the same config variables as before. To do so set DATA_MODE='from_file'. Be sure the temporal and spatial extent is consistent with the other config variables. The maridatadownloader - which is used by the WRT - can facilitate the preparation.

  3. A third option is to set up an Open Data Cube (ODC) instance. To use it set DATA_MODE='odc'. In this case, the data will be extracted from ODC and also stored in the two files as described before.

Be sure that the water depth data is available and configured correctly in order to use the water_depth option of CONSTRAINTS_LIST.

The following parameters are downloaded automatically or need to be prepared:

  • u-component_of_wind_height_above_ground (u-component of wind @ Specified height level above ground)
  • v-component_of_wind_height_above_ground (v-component of wind @ Specified height level above ground)
  • vtotal (Northward total velocity: Eulerian + Waves + Tide)
  • utotal (Eastward total velocity: Eulerian + Waves + Tide)
  • VHMO (spectral significant wave height @ sea surface)
  • VMDR (mean wave direction @ sea surface)
  • VTPK (wave period at spectral peak)
  • thetao (potential temperature)
  • Pressure_reduced_to_MSL_msl (pressure reduced to mean sea level)
  • Temperature_surface (temperature at the water surface)
  • so (salinity)

Fig. 1: Basic installation workflow for the WeatherRoutingTool.

Conventions

Coordinates

  • latitude: -90° - 90°
  • longitude: -180° - 180°
  • headings: 0° - 360°, angular difference between North and the ship's direction, angles are going in the negative mathematical direction (clockwise)

Units

Apart from one exception, the WRT uses SI units for internal calculations. Only angles are handled in degrees as defined in the paragraph above. All input variables that carry a unit are converted according to these definitions. For the output -- i.e. when a route is written to a json file -- the engine power is converted to kW and the fuel rate to mt/h, where mt refers to metric ton.

The WRT uses the package astropy for the convenient handling of units.

Logging

The routing tool writes log output using the python package logging. Information about basic settings are written to a file which is specified by the environment variable INFO_LOG_FILE. Warnings and performance information are written to the file which is specified by the environment variable PERFORMANCE_LOG_FILE. Further debug information are written to stdout.

Isofuel Algorithm

General concept

The routing process is divided into individual routing steps. For every step, the distance is calculated that the ship can travel following different courses with a specified amount of fuel and constant speed. Only those routes that maximise the travel distance for a constant amount of fuel are selected for the next routing step. This optimisation process is referred to as pruning. The distance between the start coordinates at the beginning of the routing step and the end coordinates after the step is referred to as route segment.

The algorithm is the following:

  1. Define the amount of fuel fmax that the ship can consume for every single routing step.
  2. Consider a selection of courses outgoing from the start coordinate pair. For every course, calculate the fuel rate f/t (the amount of fuel consumed per time interval) that is necessary to keep the ship speed and course.
  3. Based on f/t, fmax and the ship speed, calulate the distance that is traveled for every route segment.
  4. Divide the angular region into equally-sized segments -- the pruning segments. For every pruning segment, the end point of the route segment that maximises the distance is passed as a new starting point to the next routing step.
  5. Repeat steps 2. to 4. until the distance of any route from the starting coordinates towards the destination is smaller than the length of the route segment from the current routing step.

Obviously, the amount of fuel fmax that is provided to the algorithm determines the step width of the final route: the larger fmax, the longer the route segments and the more edgy the final route. The number ncourses of courses that is considered for every coordinate pair defines the resolution with which the area is searched for optimal routes. Thus, the smaller ncourses, the larger the likelihood that more optimal routes exist than the final route provided. On the other hand, the larger ncourses the larger is the calculation power. Further settings that can be defined are the area that is considered for the pruning as well as the number nprune of pruning segments. The later specifies the number of end points that are passed from one routing step to the next. The relation of ncourses and nprune defines the degree of optimisation.

Parameter and variable definitions

Fig.2: Schema for the definition of the most important parameters names for the isofuel algorithm.

ISOCHRONE_PRUNE_SEGMENTS = number of segments that are used for the pruning process
ISOCHRONE_PRUNE_SECTOR_DEG_HALF = angular range of azimuth angle that is considered for pruning (only one half of it!)
ROUTER_HDGS_SEGMENTS = total number of courses/azimuths/headings that are considered per coordinate pair for every routing step
ROUTER_HDGS_INCREMENTS_DEG = angular distance between two adjacent routing segments

heading/course/azimuth/variants = the angular distance towards North on the grand circle route
lats_per_step: (M,N) array of latitudes for different routes (shape N=headings+1) and routing steps (shape M=steps,decreasing)
lons_per_step: (M,N) array of longitude for different routes (shape N=headings+1) and routing steps (shape M=steps,decreasing)

Pruning methods

The pruning is the basis of the optimisation process for the isofuel algorithm. There exist three major concepts that can be used to adjust the pruning:

  1. The definition of the angular region that is used for the pruning. This is specified by the number of pruning segments, the reach of the pruning sector and, most importantly, the angle around which the pruning segments are centered -- in the following refered to as symmetry axis
  2. The choice of how route segments are grouped for the pruning.
  3. The minimisation criterion that is used as basis for the pruning.

The Definition of the Symmetry Axis

Two methods for the definition of the symmetry axis can be selected:

  1. The symmetry axis is defined by the grand circle distance between the start point and the destination. In case intermediate waypoints have been defined, the intermediat start and end point are utilised.
  2. The symmetry axis is defined by the median of the angles with respect to North of the connecting lines between the end of the route segments and the destination.

Fig.3: The symmetry axis of the pruning is given by the grand circle distance between global start and end point.

Fig.4: The symmetry axis of the pruning is given by the median of the angles of the connecting lines between the end of the route segments and the destination.

Grouping Route Segments

Route segments are organised in groups before the pruning is performed. Segments that lie outside of the pruning sector (shaded pink area in figures below) are exclueded from the pruning (dashed grey lines). The segment of one group that performs best regarding the minimisation criterion, survives the pruning process (solid pink lines). Three possibilities are available for grouping the route segments for the pruning:

  1. courses-based: Route segments are grouped according to their courses.



  1. larger-direction-based: Route segments are grouped accoding to the angle of the connecting line between the global start point and the end of the route segment.



  1. branch-based: Route segments of one branch form a group. Thus all route segments are considered for the pruning. For a particular routing step, a branch is the entity of route segments that originate from one common point.



The Minimisation Criterion

to be continued

Genetic Algorithm

General concept

Five phases:

  1. Initial population
    • Consists of candidate solutions (also called individuals) which have a set of properties (also called parameters, variables, genes)
  2. Fitness function (evaluation)
  3. Selection
  4. Crossover
  5. Mutation

Abort criteria:

  • Maximum number of generations
  • Satisfactory fitness level has been reached

Routing Problem

Phases:

  1. Initial population
    • route_through_array . Fitness function (evaluation)
    • mariPower
  2. Selection
  3. Crossover
    • only routes which cross geometrically are used for crossover
  4. Mutation
    • in principle random but can be restricted

Useful links:

Variable definitions: debug output

  • n_gen: current generation
  • n_nds: number of non-dominating solutions
  • cv_min: minimum constraint violation
  • cv_avg: average constraint violation
  • eps: epsilon?
  • indicator: indicator to monitor algorithm performance; can be Hypervolume, Running Metric ...

General Notes:

  • res.F = None: quick-and-dirty hack possible by passing 'return_least_infeasible = True' to init function of NSGAII
  • chain of function calls until RoutingProblem._evaluate() is called:
    • core/algorithms.run -> core/algorithms.next -> core/evaluator.eval -> core/evaluator._eval
  • chain of function calls until crossover/mutation/selection are called:
    • core/algorithms.run -> core/algorithms.next -> core/algorithm.infill -> algorithms/base/genetic._infill

Fuel estimation -- The communication between mariPower and the WRT

Information is transferred via a netCDF file between the WRT and mariPower. The coordinate pairs, courses, the ship speed and the time for which the power estimation needs to be performed are written to this file by the WRT. This information is read by mariPower, the calculation of the ship parameters is performed and the corresponding results are added as separate variables to the xarray dataset. The structure of the xarray dataset after the ship parameters have been written is the following:

Dimensions:                    (it_pos: 2, it_course: 3)
Coordinates:
   * it_pos                    (it_pos) int64 1 2
   * it_course                 (it_course) int64 1 2 3
Data variables:
    courses                    (it_pos, it_course) float64 ...
    speed                      (it_pos, it_course) int64 ...
    lat                        (it_pos) float64 ...
    lon                        (it_pos) float64 ...
    time                       (it_pos) datetime64[ns] ...
    Power_delivered            (it_pos, it_course) float64 ...
    RotationRate               (it_pos, it_course) float64 ...
    Fuel_consumption_rate      (it_pos, it_course) float64 ...
    Calm_resistance            (it_pos, it_course) float64 ...
    Wind_resistance            (it_pos, it_course) float64 ...
    Wave_resistance            (it_pos, it_course) float64 ...
    Shallow_water_resistance   (it_pos, it_course) float64 ...
    Hull_roughness_resistance  (it_pos, it_course) float64 ...

The coordinates it_pos and it_course are iterators for the coordinate pairs and the courses that need to be checked per coordinate pair, respectively. The function in the WRT that writes the route parameters to the netCDF file is called ship.write_netCDF_courses. Following up on this, the function get_fuel_netCDF in the WRT calls the function PredictPowerOrSpeedRoute in mariPower which itself initiates the calcualation of the ship parameters. The netCDF file is overwritten by the WRT for every routing step s.t. the size of the file is not increasing during the routing process.

Fig.2 Schema to visualise which coordinate pairs are send in a combined request to mariPower for fuel estimation in case of the isofuel algorithm. All coordinate pairs marked by orange filled circles are send for the second routing step. Coordinate pairs marked with blue filled circles are endpoints after the first routing step that survived the pruning.

Fig.3 Schema to visualise which coordinate pairs are send in a combined request to mariPower for fuel estimation in case of the genertic algorithm. All coordinate pairs marked by the same colour are send in one request.

Both for the isofuel algorithm and the genetic algorithm the same structure of the netCDF file is used. However, due to the different concepts of the algorithms, the entity of points that is send for calculation in one request differes between both algorithms. For the isofuel algorithm, all coordinate pairs and courses that are considered for a single routing step are passed to mariPower in a single request (see Fig. 2). For the genetic algorithm all points and courses for a closed route are passed in a single request (see Fig. 3).

The constraints module

The input parameters

Fig.4 Figure for illustrating the concept of passing the information on the routing segments that are to be checked by the constraint module to the respective function. Variable names printed in orange correspond to the naming scheme for the first routing step while variables printed in blue correspond to the naming scheme for the second routing step.

As described above [ToDo], the constraint module can be used to check constraints for a complete routing segment. Thereby, several routing segments can be processed in only one request. This means that for the genetic algorithm, only one request needs to be performed for every route that is considered in a single generation and for the isofuel algorithm, only one request needs to be performed for every single routing step. This implementation minimises computation time and is achieved by passing arrays of latitudes and longitudes to the constraint module i.e. if the constraint module is called like this

   safe_crossing(lat_start, lat_end, lon_start, lon_end)

then, the arguments lat_start, lat_end, lon_start and lon_end correspond to arrays for which every element characterises a different routing segment. Thus the length of the arrays is equal to the number of routing segments that are to be checked. While for the genetic algorithm, the separation of a closed route into different routing segments is rather simple, the separation for the isofuel algorithm is more complex. This is, why the passing of the latitudes and longitudes shall be explained in more detail for the isofuel algorithm in the following.

Let's consider only two routing steps of the form that is sketched in Fig. XXX. The parameters that are passed to the constraints module for the first routing step are the latitudes and longitudes of start and end points for the routing segments a to e which are

  • lat_start = (lat_startabcde, lat_startabcde, lat_startabcde, lat_startabcde, lat_startabcde)
  • lat_end = (lat_enda, latendb, latendc, latendd, latende)
  • lon_start = (lon_startabcde, lon_startabcde, lon_startabcde, lon_startabcde, lon_startabcde)
  • lon_end = (lon_enda, lon_endb, lon_endc, lon_endd, lon_ende)

i.e. since the start coordinates are matching for all routing segments, the elements for the start latitudes and longitudes are all the same.
The arguments that are passed for the second routing step are the start and end coordinates of the routing segments α to ζ:

  • lat_start = (lat_startαβγ, lat_startαβγ,lat_startαβγ,lat_startδεζ, lat_startδεζ,lat_startδεζ)
  • lat_end = (lat_endα, lat_endβ,lat_endγ,lat_endδ, lat_endε,lat_endζ)
  • lon_start = (lon_startαβγ, lon_startαβγ,lon_startαβγ,lon_startδεζ, lon_startδεζ,lon_startδεζ)
  • lon_end = (lon_endα, lon_endβ,lon_endγ,lon_endδ, lon_endε,lon_endζ)

i.e. the latitudes of the end points from the first routing step are now the start coordinates of the current routing step. In contrast to the first routing step, the start coordinates of the second routing step differ for several route segments.

Route Postprocessing

When the optional config variable ROUTE_POSTPROCESSING is enabled, the route is forwarded for postprocessing to follow Traffic Separation Scheme(TSS) rules.
Pgsnapshot schema with Osmosis were used to import OpenSeaMap data into the PostGIS+PostgreSQL database to retrieve TSS related data. The key OpenSeaMap TSS tags considered for route postprocessing are inshore_traffic_zone, separation_boundary, separation_lane, separation_boundary and separation_line. The primary TSS rules have been addressed in the current development phase are:

  1. If the current route is crossing any Inshore Traffic Zone or other TTS element, then the route should enter and leave the nearest sepeartion lane which is heading to the direction of destination.

  1. If the current route is intersecting the Traffic Separation Lanes and the angle between the route nodes before the intersection and after the intersection is between 60° to 120°, the new route segment is introduced as it is perpendicular to the separation lane and extends towards the last route segment, perpendicularly.

Furthermore, if the starting node or the ending node is located inside a traffic separation zone, route postprocessing is not further executed.

Useful links:

Developing

Style guide

Docstring

ToDo: document chosen format, relevant PEPs, etc.

reStructuredText:

  • can be used by Sphinx to generate documentation automatically
  • default in PyCharm

Example:

"""
This is a reStructuredText style.

:param param1: this is a first param
:param param2: this is a second param
:returns: this is a description of what is returned
:raises keyError: raises an exception
"""

References

Funding

Project/Logo Description
MariData MariGeoRoute is funded by the German Federal Ministry of Economic Affairs and Energy (BMWi)BMWi

About

A tool to perform optimization of ship routes based on fuel consumption in different weather conditions

Resources

Stars

Watchers

Forks

Packages

No packages published

Contributors 4

  •  
  •  
  •  
  •