Skip to content

Commit

Permalink
More fixes
Browse files Browse the repository at this point in the history
  • Loading branch information
Braktar committed Oct 21, 2021
1 parent 1f4600a commit df9fb14
Show file tree
Hide file tree
Showing 7 changed files with 58 additions and 11 deletions.
4 changes: 2 additions & 2 deletions models/solution/parsers/route_parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@

module Parsers
class RouteParser
def self.parse(route, vrp, matrix, options)
def self.parse(route, vrp, matrix, options = {})
return if route.steps.empty?

@route = route
Expand Down Expand Up @@ -66,7 +66,7 @@ def self.compute_route_total_dimensions(matrix)
}
end

previous_index = matrix_index
previous_index = matrix_index if activity.type != :rest
}

if @route.info.end_time && @route.info.start_time
Expand Down
2 changes: 1 addition & 1 deletion models/solution/parsers/solution_parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@

module Parsers
class SolutionParser
def self.parse(solution, vrp, options)
def self.parse(solution, vrp, options = {})
tic_parse_result = Time.now
vrp.vehicles.each{ |vehicle|
route = solution.routes.find{ |r| r.vehicle.id == vehicle.id }
Expand Down
24 changes: 24 additions & 0 deletions models/solution/route.rb
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,30 @@ def vrp_result(options = {})
def count_services
steps.count(&:service_id)
end

def insert_step(vrp, step_object, index)
matrix = vrp.matrices.find{ |m| m.id == vehicle.matrix_id }
steps.insert(index, step_object)
shift_route_times(step_object.activity.duration, index)
Parsers::RouteParser.parse(self, vrp, matrix)
end

def shift_route_times(shift_amount, shift_start_index = 0)
return if shift_amount == 0

raise 'Cannot shift the route, there are not enough steps' if shift_start_index > self.steps.size

self.info.start_time += shift_amount if shift_start_index == 0
self.steps.each_with_index{ |step_object, index|
next if index <= shift_start_index

step_object.info.begin_time += shift_amount
step_object.info.end_time += shift_amount if step_object.info.end_time
step_object.info.departure_time += shift_amount if step_object.info.departure_time
step_object.info.waiting_time = [step_object.info.waiting_time - shift_amount, 0].max
}
self.info.end_time += shift_amount if self.info.end_time
end
end
end
end
5 changes: 5 additions & 0 deletions models/solution/solution.rb
Original file line number Diff line number Diff line change
Expand Up @@ -96,5 +96,10 @@ def update_costs
cost_info = routes.map(&:cost_info).sum
self.cost -= (previous_total - cost_info.total).round
end

def insert_step(vrp, route, step_object, index)
route.insert_step(vrp, step_object, index)
Parsers::SolutionParser.parse(self, vrp)
end
end
end
2 changes: 1 addition & 1 deletion test/wrappers/ortools_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -5164,7 +5164,7 @@ def test_pause_should_be_last_if_possible

solutions = OptimizerWrapper.wrapper_vrp('demo', { services: { vrp: [:ortools] }}, TestHelper.create(vrp), nil)

assert solutions[0].routes.first.steps[-2][:rest_id], 'Pause should be at the last spot'
assert solutions[0].routes.first.steps[-2].type == :rest, 'Pause should be at the last spot'
end

def test_no_nil_in_corresponding_mission_ids
Expand Down
26 changes: 22 additions & 4 deletions wrappers/ortools.rb
Original file line number Diff line number Diff line change
Expand Up @@ -438,10 +438,28 @@ def build_route_step(vrp, vehicle, activity)
def build_routes(vrp, routes)
@vehicle_rest_ids = Hash.new([])
routes.map.with_index{ |route, index|
previous_matrix_index = nil
vehicle = vrp.vehicles[index]
route_costs = build_cost_details(route.cost_details)
steps = route.activities.map{ |activity|
build_route_step(vrp, vehicle, activity)
current_matrix_index =
case activity.type
when 'service'
service = vrp.services[activity.index]
service.activity&.point&.matrix_index ||
!service.activities.empty? && service.activities[activity.alternative].point.matrix_index
when 'start'
vrp.vehicles[index].start_point&.matrix_index
when 'end'
vrp.vehicles[index].end_point&.matrix_index
end
step_object = build_route_step(vrp, vehicle, activity)
next step_object if activity.type == 'rest'

matrix = vrp.matrices.find{ |m| m.id == vehicle.matrix_id }
build_route_data(step_object, matrix, previous_matrix_index, current_matrix_index)
previous_matrix_index = current_matrix_index
step_object
}.compact
route_detail = Models::Solution::Route::Info.new({})
initial_loads = route.activities.first.quantities.map.with_index{ |quantity, q_index|
Expand Down Expand Up @@ -485,16 +503,16 @@ def check_services_compatible_days(vrp, vehicle, service)
vehicle.global_day_index.between?(service.first_possible_days.first, service.last_possible_days.first)
end

def build_route_data(vehicle_matrix, previous_matrix_index, current_matrix_index)
def build_route_data(step, vehicle_matrix, previous_matrix_index, current_matrix_index)
if previous_matrix_index && current_matrix_index
travel_distance = vehicle_matrix[:distance] ? vehicle_matrix[:distance][previous_matrix_index][current_matrix_index] : 0
travel_time = vehicle_matrix[:time] ? vehicle_matrix[:time][previous_matrix_index][current_matrix_index] : 0
travel_value = vehicle_matrix[:value] ? vehicle_matrix[:value][previous_matrix_index][current_matrix_index] : 0
return {
{
travel_distance: travel_distance,
travel_time: travel_time,
travel_value: travel_value
}
}.each{ |key, value| step.info.send("#{key}=", value) }
end
{}
end
Expand Down
6 changes: 3 additions & 3 deletions wrappers/wrapper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -1279,10 +1279,10 @@ def simplify_vehicle_pause(vrp, result = nil, options = { mode: :simplify })
idle_time_created_by_inserted_pause = 0
end
times = { begin_time: rest_start, end_time: rest_start + rest.duration, departure_time: rest_start + rest.duration }
route.steps.insert(insert_rest_at,
Models::Solution::Step.new(rest, info: Models::Solution::Step::Info.new(times)))
rest_step = Models::Solution::Step.new(rest, info: Models::Solution::Step::Info.new(times))
result.insert_step(vrp, route, rest_step, insert_rest_at)

shift_route_times(route, idle_time_created_by_inserted_pause + rest.duration, insert_rest_at + 1)
# shift_route_times(route, idle_time_created_by_inserted_pause + rest.duration, insert_rest_at + 1)

next if no_cost

Expand Down

0 comments on commit df9fb14

Please sign in to comment.