From 99a07094fcf7ab2f8db52582e6824a27a3890fd2 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Tue, 12 Jul 2022 16:59:45 +0200 Subject: [PATCH] Remove the Dictionary for the moving section --- src/TrainRuns.jl | 12 +++++------ src/behavior.jl | 21 ++++++++----------- src/calc.jl | 42 +++++++++++++++++++++++--------------- src/constructors.jl | 49 +++++++++++---------------------------------- 4 files changed, 52 insertions(+), 72 deletions(-) diff --git a/src/TrainRuns.jl b/src/TrainRuns.jl index 754a3e6..5cf5801 100644 --- a/src/TrainRuns.jl +++ b/src/TrainRuns.jl @@ -46,15 +46,15 @@ xxx.xx # in seconds """ function trainrun(train::Train, path::Path, settings=Settings()::Settings) # prepare the input data - movingSection = determineCharacteristics(path, train, settings) - # settings.outputDetail == :verbose && println("The moving section has been prepared.") + (characteristicSections, pointsOfInterest) = determineCharacteristics(path, train, settings) + # TODO settings.outputDetail == :verbose && println("The characteristics haven been determined.") - # calculate the train run for oparation mode "minimum running time" - (movingSection, drivingCourse) = calculateMinimumRunningTime!(movingSection, settings, train) - # settings.outputDetail == :verbose && println("The driving course for the shortest running time has been calculated.") + # calculate the train run with the minimum running time + (characteristicSections, drivingCourse) = calculateMinimumRunningTime!(characteristicSections, settings, train) + # TODO settings.outputDetail == :verbose && println("The driving course for the shortest running time has been calculated.") # accumulate data and create an output dictionary - output = createOutput(settings, drivingCourse, movingSection[:pointsOfInterest]) + output = createOutput(settings, drivingCourse, pointsOfInterest) return output end # function trainrun diff --git a/src/behavior.jl b/src/behavior.jl index 2c05027..f64d817 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -107,11 +107,8 @@ end #function addClearingSection ## This function calculates the support points of the accelerating section. # Therefore it gets its previous driving course and the characteristic section and returns the characteristic section and driving course including the accelerating section function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) - #function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, settings::Settings, train::Train, CSs::Vector{Dict}, ignoreBraking::Bool) - #=if drivingCourse would also be part of movingSectiong: function addAcceleratingSection!(movingSection::Dict, stateFlags::Dict, csId::Integer, settings::Settings, train::Train) - CSs = movingSection[:characteristicSections] - CS = CSs[csId] - drivingCourse = movingSection[:drivingCourse]=# +#= TODO: instead of CS just give csId? + -> CS = CSs[csId] =# calculateForces!(drivingCourse[end], CSs, CS[:id], "accelerating", train, settings.massModel) @@ -1176,9 +1173,8 @@ function recalculateLastBrakingPoint!(drivingCourse, s_target, v_target) end #function recalculateLastBrakingPoint ## define the intersection velocities between the characterisitc sections to secure braking behavior -function secureBrakingBehavior!(movingSection::Dict, a_braking::Real, approxLevel::Integer) - # this function limits the entry and exit velocity of the characteristic sections to secure that the train stops at the moving sections end - CSs = movingSection[:characteristicSections] +function secureBrakingBehavior!(CSs::Vector{Dict}, a_braking::Real, approxLevel::Integer) + # limit the entry and exit velocity of the characteristic sections to secure that the train stops at the moving sections end csId = length(CSs) followingCSv_entry = 0.0 # the exit velocity of the last characteristic section is 0.0 m/s @@ -1200,13 +1196,12 @@ function secureBrakingBehavior!(movingSection::Dict, a_braking::Real, approxLeve followingCSv_entry = CS[:v_entry] csId = csId - 1 end #while - return movingSection + return CSs end #function secureBrakingBehavior! ## define the intersection velocities between the characterisitc sections to secure accelerating behavior -function secureAcceleratingBehavior!(movingSection::Dict, settings::Settings, train::Train) - # this function limits the entry and exit velocity of the characteristic sections in case that the train accelerates in every section and cruises aterwards - CSs = movingSection[:characteristicSections] +function secureAcceleratingBehavior!(CSs::Vector{Dict}, settings::Settings, train::Train) + # limit the entry and exit velocity of the characteristic sections in case that the train accelerates in every section and cruises afterwards CSs[1][:v_entry] = 0.0 # the entry velocity of the first characteristic section is 0.0 m/s startingPoint = SupportPoint() @@ -1264,5 +1259,5 @@ function secureAcceleratingBehavior!(movingSection::Dict, settings::Settings, tr CS[:t] = 0.0 end #for - return movingSection + return CSs end #function secureAcceleratingBehavior! diff --git a/src/calc.jl b/src/calc.jl index 66d52e8..349766f 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -7,12 +7,11 @@ # Calculate the running time of a train run on a path with special settings with information from the corresponding YAML files with the file paths `trainDirectory`, `pathDirectory`, `settingsDirectory`. # calculate a train run focussing on using the minimum possible running time -function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, train::Train) - CSs::Vector{Dict} = movingSection[:characteristicSections] +function calculateMinimumRunningTime!(CSs::Vector{Dict}, settings::Settings, train::Train) if settings.massModel == :homogeneous_strip && settings.stepVariable == speed println("WARNING: ! ! ! TrainRuns.jl doesn't work reliably for the mass model homogeneous strip with step size v in m/s. The calculation time can be extremely high when calcutlating paths with steep gradients ! ! !") - end + end # TODO startingPoint = SupportPoint() startingPoint[:i] = 1 @@ -22,7 +21,7 @@ function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, t for csId in 1:length(CSs) CS = CSs[csId] - # for testing + # for testing: # TODO if drivingCourse[end][:s] != CS[:s_entry] println("ERROR: In CS", csId," the train run starts at s=",drivingCourse[end][:s]," and not s_entry=",CS[:s_entry]) end @@ -106,7 +105,7 @@ function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, t #end - # for testing: + # for testing: # TODO if drivingCourse[end][:s] != CS[:s_exit] println("ERROR: In CS", csId," the train run ends at s=",drivingCourse[end][:s]," and not s_exit=",CS[:s_exit]) end @@ -117,9 +116,7 @@ function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, t (CSs[end], drivingCourse) = addHalt!(CSs[end], drivingCourse, settings, train, CSs) - movingSection[:t] = drivingCourse[end][:t] # total running time (in s) - - return (movingSection, drivingCourse) + return (CSs, drivingCourse) end #function calculateMinimumRunningTime @@ -180,7 +177,7 @@ function calculatePathResistance(CSs::Vector{Dict}, csId::Integer, s::Real, mass pathResistance = pathResistance + (min(s, CSs[csId][:s_exit]) - max(s_rear, CSs[csId][:s_entry])) / train.length * forceFromCoefficient(CSs[csId][:r_path], train.m_train_full) csId = csId-1 if csId == 0 - # TODO: currently for values < movingSection[:s_entry] the values of movingSection[:s_entry] will be used + # TODO: currently for values < s_trainrun_start the values of s_trainrun_start will be used return pathResistance + (CSs[1][:s_entry] - s_rear) / train.length * forceFromCoefficient(CSs[1][:r_path], train.m_train_full) end #if end #while @@ -289,7 +286,7 @@ function getCurrentSpeedLimit(CSs::Vector{Dict}, csWithTrainHeadId::Integer, s:: if csWithTrainHeadId > 1 && s -trainLength < CSs[csWithTrainHeadId][:s_entry] formerCsId = csWithTrainHeadId-1 while formerCsId > 0 && s -trainLength < CSs[formerCsId][:s_exit] - if CSs[formerCsId][:v_limit] < v_limit # TODO: is the position of the train's rear < movingSection[:s_entry], v_limit of the first CS is used + if CSs[formerCsId][:v_limit] < v_limit # TODO: is the position of the train's rear < s_trainrun_start, v_limit of the first CS is used v_limit = CSs[formerCsId][:v_limit] s_exit = CSs[formerCsId][:s_exit] end @@ -314,12 +311,25 @@ function getNextPointOfInterest(pointsOfInterest::Vector{Tuple}, s::Real) end #function getNextPointOfInterest -## create a moving section and its containing characteristic sections with secured braking, accelerating and cruising behavior +## create vectors with the moving section's points of interest and with the characteristic sections with secured braking and accelerating behavior function determineCharacteristics(path::Path, train::Train, settings::Settings) - movingSection = MovingSection(path, train.v_limit, train.length) - movingSection = secureBrakingBehavior!(movingSection, train.a_braking, settings.approxLevel) - movingSection = secureAcceleratingBehavior!(movingSection, settings, train) - #movingSection = secureCruisingBehavior!(movingSection, settings, train) + # determine the positions of the points of interest depending on the interesting part of the train (front/rear) and the train's length + ##TODO: use a tuple with naming + pointsOfInterest = Tuple[] + if !isempty(path.poi) + for POI in path.poi + s_poi = POI[:station] + if POI[:measure] == "rear" + s_poi += train.length + end + push!(pointsOfInterest, (s_poi, POI[:label]) ) + end + sort!(pointsOfInterest, by = x -> x[1]) + end - return movingSection + characteristicSections = CharacteristicSections(path, train.v_limit, train.length, pointsOfInterest) + characteristicSections = secureBrakingBehavior!(characteristicSections, train.a_braking, settings.approxLevel) + characteristicSections = secureAcceleratingBehavior!(characteristicSections, settings, train) + + return (characteristicSections, pointsOfInterest) end #function determineCharacteristics diff --git a/src/constructors.jl b/src/constructors.jl index fe90a88..2b89c4d 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -254,9 +254,9 @@ function Path(file, type = :YAML) if POI_PRESENT sort!(tmp_points, by = x -> x[1]) for elem in tmp_points - station = elem[1] # first point of the section (in m) - label = elem[2] # paths speed limt (in m/s) - measure = elem[3] # specific path resistance of the section (in ‰) + station = elem[1] # station in m + label = elem[2] # name + measure = elem[3] # front or rear point = Dict(:station => station, :label => label, @@ -613,53 +613,28 @@ function Train(file, type = :YAML) end #function Train() # outer constructor -## create a moving section containing characteristic sections -function MovingSection(path::Path, v_trainLimit::Real, s_trainLength::Real) - # this function creates and returns a moving section dependent on the paths attributes - - s_entry = path.sections[1][:s_start] # first position (in m) - s_exit = path.sections[end][:s_end] # last position (in m) - pathLength = s_exit - s_entry # total length (in m) - - ##TODO: use a tuple with naming - pointsOfInterest = Tuple[] - if !isempty(path.poi) - for POI in path.poi - s_poi = POI[:station] - if POI[:measure] == "rear" - s_poi += s_trainLength - end - push!(pointsOfInterest, (s_poi, POI[:label]) ) - end - sort!(pointsOfInterest, by = x -> x[1]) - end +## create the moving section's characteristic sections +function CharacteristicSections(path::Path, v_trainLimit::Real, s_trainLength::Real, MS_poi::Vector{Tuple}) + # create and return the characteristic sections of a moving section dependent on the paths attributes CSs=Vector{Dict}() - s_csStart=s_entry - csId=1 + s_csStart = path.sections[1][:s_start] # first position (in m) + csId = 1 for row in 2:length(path.sections) previousSection = path.sections[row-1] currentSection = path.sections[row] speedLimitIsDifferent = min(previousSection[:v_limit], v_trainLimit) != min(currentSection[:v_limit], v_trainLimit) pathResistanceIsDifferent = previousSection[:f_Rp] != currentSection[:f_Rp] if speedLimitIsDifferent || pathResistanceIsDifferent - push!(CSs, CharacteristicSection(csId, s_csStart, previousSection, min(previousSection[:v_limit], v_trainLimit), s_trainLength, pointsOfInterest)) + push!(CSs, CharacteristicSection(csId, s_csStart, previousSection, min(previousSection[:v_limit], v_trainLimit), s_trainLength, MS_poi)) s_csStart = currentSection[:s_start] csId = csId+1 end #if end #for - push!(CSs, CharacteristicSection(csId, s_csStart, path.sections[end], min(path.sections[end][:v_limit], v_trainLimit), s_trainLength, pointsOfInterest)) + push!(CSs, CharacteristicSection(csId, s_csStart, path.sections[end], min(path.sections[end][:v_limit], v_trainLimit), s_trainLength, MS_poi)) - movingSection= Dict(:id => 1, # identifier # if there is more than one moving section in a later version of this tool the id should not be constant anymore - :length => pathLength, # total length (in m) - :s_entry => s_entry, # first position (in m) - :s_exit => s_exit, # last position (in m) - :t => 0.0, # total running time (in s) - :characteristicSections => CSs, # list of containing characteristic sections - :pointsOfInterest => pointsOfInterest) # list of containing points of interest - - return movingSection -end #function MovingSection + return CSs +end #function CharacteristicSections ## create a characteristic section for a path section. A characteristic section is a part of the moving section. It contains behavior sections. function CharacteristicSection(id::Integer, s_entry::Real, section::Dict, v_limit::Real, s_trainLength::Real, MS_poi::Vector{Tuple})