From 3626f46df90d1fd3e8cd5901fb7adbbebcdc734d Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Fri, 12 Aug 2022 17:52:35 +0200 Subject: [PATCH 01/14] Fix typing error (change :speed to :velocity) --- src/behavior.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/behavior.jl b/src/behavior.jl index 4649260..ff89da8 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -188,7 +188,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla elseif drivingCourse[end][:v] > CS[:v_peak] testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_peak=",CS[:v_peak]) # for testing - if settings.stepVariable == :speed + if settings.stepVariable == :velocity currentStepSize = CS[:v_peak]-drivingCourse[end-1][:v] else currentStepSize = settings.stepSize / 10.0^cycle From c4d8b2c79c49d2648768010ef69b59383bb9c307 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Tue, 16 Aug 2022 12:25:50 +0200 Subject: [PATCH 02/14] Remove key :length from CharacteristicSection dictionary --- src/behavior.jl | 2 +- src/constructors.jl | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index ff89da8..e05aba7 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -1069,7 +1069,7 @@ function secureBrakingBehavior!(CSs::Vector{Dict}, a_braking::Real, approxLevel: CS[:v_exit] = min(CS[:v_limit], followingCSv_entry) - v_entryMax = brakingStartVelocity(CS[:v_exit], a_braking, CS[:length], approxLevel) + v_entryMax = brakingStartVelocity(CS[:v_exit], a_braking, CS[:s_exit]-CS[:s_entry], approxLevel) CS[:v_entry] = min(CS[:v_limit], v_entryMax) CS[:v_peak] = CS[:v_entry] diff --git a/src/constructors.jl b/src/constructors.jl index 7d93711..39001f0 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -642,7 +642,6 @@ function CharacteristicSection(id::Integer, s_entry::Real, section::Dict, v_limi characteristicSection::Dict{Symbol, Any} = Dict(:id => id, # identifier :s_entry => s_entry, # first position (in m) :s_exit => section[:s_end], # last position (in m) - :length => section[:s_end] -s_entry, # total length (in m) :r_path => section[:f_Rp], # path resistance (in ‰) :v_limit => v_limit, # speed limit (in m/s) # initializing :v_entry, :v_peak and :v_exit with :v_limit From f11e64b8b84a92570b9a7b90f906a7340d1cc703 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Tue, 16 Aug 2022 23:23:02 +0200 Subject: [PATCH 03/14] Remove key :v_peak from CharacteristicSection dictionary --- src/behavior.jl | 136 ++++++++++++++++++++------------------------ src/constructors.jl | 3 +- 2 files changed, 62 insertions(+), 77 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index e05aba7..5193894 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -107,23 +107,21 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end # conditions for the accelerating section - targetSpeedReached = drivingCourse[end][:v] >= CS[:v_peak] || stateFlags[:speedLimitReached] endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached] tractionSurplus = drivingCourse[end][:F_T] > drivingCourse[end][:F_R] brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] || stateFlags[:brakingStartReached] previousSpeedLimitReached = stateFlags[:previousSpeedLimitReached] + speedLimitReached = drivingCourse[end][:v] >= CS[:v_limit] || stateFlags[:speedLimitReached] # use the conditions for the accelerating section - if !targetSpeedReached && !endOfCSReached && tractionSurplus && !brakingStartReached + if !speedLimitReached && !endOfCSReached && tractionSurplus && !brakingStartReached drivingMode = "accelerating" drivingCourse[end][:behavior] = drivingMode currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) previousSpeedLimitReached = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= currentSpeedLimit[:v] - speedLimitReached = drivingCourse[end][:v] >= CS[:v_limit] - #speedLimitReached = drivingCourse[end][:v] > currentSpeedLimit[:v] - #targetSpeedReached = speedLimitReached - while !targetSpeedReached && !endOfCSReached && tractionSurplus && !brakingStartReached && !previousSpeedLimitReached + + while !speedLimitReached && !endOfCSReached && tractionSurplus && !brakingStartReached && !previousSpeedLimitReached currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] @@ -133,10 +131,9 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) end - while !targetSpeedReached && !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached - # 03/08 old: while drivingCourse[end][:v] < CS[:v_peak] && drivingCourse[end][:v] <= currentSpeedLimit[:v] && !brakingStartReached && drivingCourse[end][:s] < nextPointOfInterest[1] && drivingCourse[end][:F_T] > drivingCourse[end][:F_R] # as long as s_i + s_braking < s_CSexit + while !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached if drivingCourse[end][:s] >= currentSpeedLimit[:s_end] - # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit will be noticed. On the other hand the train cruises possibly a little to long + # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. On the other hand the train cruises possibly a little to long currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) end @@ -154,10 +151,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) end brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] - speedLimitReached = drivingCourse[end][:v] > CS[:v_limit] + speedLimitReached = drivingCourse[end][:v] >= CS[:v_limit] previousSpeedLimitReached = currentSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > currentSpeedLimit[:v] || (drivingCourse[end][:v] == currentSpeedLimit[:v] && drivingCourse[end][:s] < currentSpeedLimit[:s_end])) - targetSpeedReached = drivingCourse[end][:v] >= CS[:v_peak] - #targetSpeedReached = speedLimitReached pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] # POIs include s_exit as well tractionSurplus = drivingCourse[end][:F_T] > drivingCourse[end][:F_R] end #while @@ -186,19 +181,10 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla currentStepSize = settings.stepSize / 10.0^cycle end - elseif drivingCourse[end][:v] > CS[:v_peak] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_peak=",CS[:v_peak]) # for testing - if settings.stepVariable == :velocity - currentStepSize = CS[:v_peak]-drivingCourse[end-1][:v] - else - currentStepSize = settings.stepSize / 10.0^cycle - end - elseif drivingCourse[end][:v] > currentSpeedLimit[:v] testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=",currentSpeedLimit[:v]) # for testing if settings.stepVariable == :velocity - currentStepSize = currentSpeedLimit[:v]-drivingCourse[end-1][:v] - + currentStepSize = currentSpeedLimit[:v] - drivingCourse[end-1][:v] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -210,11 +196,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end break - elseif drivingCourse[end][:v] == CS[:v_peak] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_peak=",CS[:v_peak]) # for testing - break - - elseif drivingCourse[end][:v] == currentSpeedLimit[:v] && drivingCourse[end][:s] < currentSpeedLimit[:s_end] + elseif drivingCourse[end][:v] == currentSpeedLimit[:v] testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_limitCurrent=",currentSpeedLimit[:v]) # for testing break @@ -226,11 +208,11 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla break else - println("v=",drivingCourse[end][:v]," v_peak= ", CS[:v_peak] , " v_cLimit=", currentSpeedLimit[:v]) + println("v=",drivingCourse[end][:v]," v_limit= ", CS[:v_limit] , " v_currentLimit=", currentSpeedLimit[:v]) println("s=" ,drivingCourse[end][:s]," s_exit=", CS[:s_exit], " s+s_braking=", drivingCourse[end][:s] +s_braking," nextPOI=",nextPointOfInterest[1]) println("F_T=",drivingCourse[end][:F_T] ," F_R=", drivingCourse[end][:F_R]) - error("ERROR at accelerating section: With the step variable ",settings.stepVariable," the while loop will be left although v CS[:v_peak] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_peak=",CS[:v_peak]) # for testing + if drivingCourse[end][:v] > currentSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=",currentSpeedLimit[:v], "with v_limit=",CS[:v_limit]) # for testing pop!(drivingCourse) # conditions for the next section @@ -268,12 +249,6 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla elseif drivingCourse[end][:F_T] <= drivingCourse[end][:F_R] testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," <= F_R=",drivingCourse[end][:F_R]) # for testing - elseif drivingCourse[end][:v] > currentSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=",currentSpeedLimit[:v]) # for testing - previousSpeedLimitReached = true - - pop!(drivingCourse) - else if drivingCourse[end][:s] + s_braking == CS[:s_exit] testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," else case and there: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing @@ -307,8 +282,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla stateFlags[:tractionDeficit] = !(tractionSurplus || drivingCourse[end][:F_T] == drivingCourse[end][:F_R]) # or add another flag for equal forces? stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0 stateFlags[:previousSpeedLimitReached] = previousSpeedLimitReached - stateFlags[:speedLimitReached] = targetSpeedReached - stateFlags[:error] = !(endOfCSReached || brakingStartReached || stateFlags[:tractionDeficit] || previousSpeedLimitReached || targetSpeedReached) + stateFlags[:speedLimitReached] = speedLimitReached + stateFlags[:error] = !(endOfCSReached || brakingStartReached || stateFlags[:tractionDeficit] || previousSpeedLimitReached || speedLimitReached) return (CS, drivingCourse, stateFlags) end #function addAcceleratingSection! @@ -338,13 +313,12 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: # conditions for cruising section #s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) brakingStartReached = drivingCourse[end][:s] + s_braking >= CS[:s_exit] || stateFlags[:brakingStartReached] - speedIsValid = drivingCourse[end][:v]>0.0 && drivingCourse[end][:v]<=CS[:v_peak] + speedIsValid = drivingCourse[end][:v] > 0.0 && drivingCourse[end][:v] <= CS[:v_limit] tractionDeficit = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] targetPositionReached = s_cruising == 0.0 resistingForceNegative = drivingCourse[end][:F_R] < 0 if speedIsValid && !brakingStartReached && !tractionDeficit && !targetPositionReached - # 03/04 old: if drivingCourse[end][:v]>0.0 && drivingCourse[end][:v]<=CS[:v_peak] && !brakingStartReached && drivingCourse[end][:F_T] >= drivingCourse[end][:F_R] drivingMode = cruisingType drivingCourse[end][:behavior] = drivingMode # TODO: necessary? @@ -363,9 +337,8 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: trainInPreviousCS = drivingCourse[end][:s] < CS[:s_entry] + train.length targetPositionReached = drivingCourse[end][:s] >= targetPosition resistingForceNegative = drivingCourse[end][:F_R] < 0.0 -# targetSpeedReached = stateFlags[:speedLimitReached] || drivingCourse[end][:v] >= CS[:v_peak] - # TODO: change? to correctCruisingType = (trainIsClearing || (trainIsBrakingDownhill == drivingCourse[end][:F_R] < 0)) # while clearing tractive or braking force can be used -#&& targetSpeedReached + # TODO: change? to: correctCruisingType = (trainIsClearing || (trainIsBrakingDownhill == drivingCourse[end][:F_R] < 0)) # while clearing tractive or braking force can be used + # use the conditions for the cruising section while trainInPreviousCS && !targetPositionReached && !tractionDeficit && (trainIsClearing || (trainIsBrakingDownhill == resistingForceNegative)) # while clearing tractive or braking force can be used currentStepSize = settings.stepSize @@ -374,7 +347,7 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while trainInPreviousCS && !targetPositionReached && !pointOfInterestReached && !tractionDeficit && (trainIsClearing || (trainIsBrakingDownhill == resistingForceNegative)) # while clearing tractive or braking force can be used - # the tractive effort is lower than the resisiting forces and the train has use the highest possible effort to try to stay at v_peak OR the mass model homogeneous strip is used and parts of the train are still in former CS + # the tractive effort is lower than the resisting forces and the train has to use the highest possible effort to try to stay at v_limit OR the mass model homogeneous strip is used and parts of the train are still in former CS #TODO: maybe just consider former CS with different path resistance? # tractive effort (in N): if !trainIsBrakingDownhill @@ -725,7 +698,7 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag stateFlags[:brakingStartReached] = brakingStartReached stateFlags[:tractionDeficit] = tractionDeficit stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0 - stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_peak] + stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_limit] stateFlags[:error] = !(endOfCSReached || brakingStartReached || !tractionDeficit) return (CS, drivingCourse, stateFlags) @@ -735,11 +708,12 @@ end #function addDiminishingSection! ## This function calculates the support points of the coasting section. # Therefore it gets its previous driving course and the characteristic section and returns the characteristic section and driving course including the coasting section function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) - # TODO: if the rear of the train is still located in a former characteristic section it has to be checked if its speed limit can be kept - # with getCurrentSpeedLimit # conditions for coasting section - targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] + currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + previousSpeedLimitReached = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] > currentSpeedLimit[:v] + speedLimitReached = drivingCourse[end][:v] > CS[:v_limit] + targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || previousSpeedLimitReached || speedLimitReached endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached] s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) @@ -757,7 +731,11 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while !targetSpeedReached && !brakingStartReached && !pointOfInterestReached - # 03/09 old : while drivingCourse[end][:v] > CS[:v_exit] && drivingCourse[end][:v] <= CS[:v_peak] && !brakingStartReached && drivingCourse[end][:s] < nextPointOfInterest[1] + if drivingCourse[end][:s] >= currentSpeedLimit[:s_end] + # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. + currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + end + # traction effort and resisting forces (in N): calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) @@ -772,7 +750,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) brakingStartReached = drivingCourse[end][:s] + s_braking >= CS[:s_exit] pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] - targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || drivingCourse[end][:v] > CS[:v_peak] + targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || drivingCourse[end][:v] > CS[:v_limit] || currentSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > currentSpeedLimit[:v] || (drivingCourse[end][:v] == currentSpeedLimit[:v] && drivingCourse[end][:s] < currentSpeedLimit[:s_end])) end # while testFlag = false @@ -785,7 +763,6 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: elseif drivingCourse[end][:s] > nextPointOfInterest[1] testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing - if settings.stepVariable == :distance currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] else @@ -794,18 +771,20 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: elseif drivingCourse[end][:v] < CS[:v_exit] # TODO: if accelereation and coasting functions will be combined this case is only for coasting testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," < v_exit=", CS[:v_exit]) # for testing - if settings.stepVariable == :velocity - currentStepSize = drivingCourse[end-1][:v] - CS[:v_exit] - else - currentStepSize = settings.stepSize / 10.0^cycle - end - elseif drivingCourse[end][:v] > CS[:v_peak] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," > v_peak=", CS[:v_peak]) # for testing if settings.stepVariable == :velocity - currentStepSize = CS[:v_peak] - drivingCourse[end-1][:v] + currentStepSize = drivingCourse[end-1][:v] - CS[:v_exit] else currentStepSize = settings.stepSize / 10.0^cycle end + + elseif drivingCourse[end][:v] > currentSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=", currentSpeedLimit[:v]) # for testing + if settings.stepVariable == :velocity + currentStepSize = currentSpeedLimit[:v] - drivingCourse[end-1][:v] + else + currentStepSize = settings.stepSize / 10.0^cycle + end + elseif drivingCourse[end][:s] + s_braking == CS[:s_exit] testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing break @@ -820,7 +799,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: else # TODO: not needed. just for testing - error("ERROR at coasting until braking section: With the step variable ",settings.stepVariable," the while loop will be left although v CS[:v_peak] # if the train gets to fast it has to brake # TODO: if accelereation and coasting functions will be combined this case is different for coasting and also the order of if cases is different + elseif drivingCourse[end][:v] > currentSpeedLimit[:v] # if the train gets to fast it has to brake to hold the velocity limit # delete last support point because it went to far pop!(drivingCourse) # conditions for the next for cycle brakingStartReached = false pointOfInterestReached = false - # targetSpeedReached = true + if currentSpeedLimit[:v] != CS[:v_limit] + previousSpeedLimitReached = true + else + speedLimitReached = true + end elseif drivingCourse[end][:s] > nextPointOfInterest[1] drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest @@ -868,8 +851,6 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: end end #while - - stateFlags[:speedLimitReached] = false end # set state flags @@ -877,7 +858,9 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: stateFlags[:brakingStartReached] = brakingStartReached stateFlags[:tractionDeficit] = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0 - stateFlags[:error] = !(endOfCSReached || brakingStartReached || stateFlags[:tractionDeficit] || previousSpeedLimitReached || targetSpeedReached) + stateFlags[:previousSpeedLimitReached] = previousSpeedLimitReached + stateFlags[:speedLimitReached] = speedLimitReached + stateFlags[:error] = !(endOfCSReached || brakingStartReached || stateFlags[:tractionDeficit] || previousSpeedLimitReached || speedLimitReached) return (CS, drivingCourse, stateFlags) end #function addCoastingSection! @@ -1072,7 +1055,6 @@ function secureBrakingBehavior!(CSs::Vector{Dict}, a_braking::Real, approxLevel: v_entryMax = brakingStartVelocity(CS[:v_exit], a_braking, CS[:s_exit]-CS[:s_entry], approxLevel) CS[:v_entry] = min(CS[:v_limit], v_entryMax) - CS[:v_peak] = CS[:v_entry] followingCSv_entry = CS[:v_entry] csId = csId - 1 @@ -1096,7 +1078,7 @@ function secureAcceleratingBehavior!(CSs::Vector{Dict}, settings::Settings, trai calculateForces!(startingPoint, CSs, CS[:id], "accelerating", train, settings.massModel) # traction effort and resisting forces (in N) acceleratingCourse::Vector{Dict} = [startingPoint] # List of support points - if CS[:v_entry] < CS[:v_peak] + if CS[:v_entry] < CS[:v_limit] # conditions for entering the accelerating phase stateFlags = Dict(:endOfCSReached => false, :brakingStartReached => false, @@ -1106,7 +1088,7 @@ function secureAcceleratingBehavior!(CSs::Vector{Dict}, settings::Settings, trai :speedLimitReached => false, :error => false, :usedForDefiningCharacteristics => true) # because usedForDefiningCharacteristics == true the braking distance will be ignored during securing the accelerating phase - v_peak = CS[:v_entry] + v_peak = CS[:v_entry] # maximum reachable speed in this CS (in m/s) (CS, acceleratingCourse, stateFlags) = addBreakFreeSection!(CS, acceleratingCourse, stateFlags, settings, train, CSs) while !stateFlags[:speedLimitReached] && !stateFlags[:endOfCSReached] if !stateFlags[:tractionDeficit] @@ -1123,13 +1105,17 @@ function secureAcceleratingBehavior!(CSs::Vector{Dict}, settings::Settings, trai (CS, acceleratingCourse, stateFlags) = addDiminishingSection!(CS, acceleratingCourse, stateFlags, settings, train, CSs) # this function is needed in case the resisitng forces are higher than the maximum possible tractive effort end end - v_peak = max(v_peak, acceleratingCourse[end][:v]) + v_peak = max(v_peak, acceleratingCourse[end][:v]) end - # CS[:v_peak] = max(CS[:v_entry], acceleratingCourse[end][:v]) - CS[:v_peak] = v_peak - CS[:v_exit] = min(CS[:v_exit], CS[:v_peak], acceleratingCourse[end][:v]) - else #CS[:v_entry] == CS[:v_peak] + if v_peak == acceleratingCourse[end][:v] && CS[:v_limit] - acceleratingCourse[end][:v] < 1/(10^settings.approxLevel) + v_peak = CS[:v_limit] + else + v_peak = acceleratingCourse[end][:v] + end + CS[:v_exit] = min(CS[:v_exit], v_peak) + + #else CS[:v_entry] == CS[:v_limit] # v_exit stays the same end #if diff --git a/src/constructors.jl b/src/constructors.jl index 39001f0..c6ec5b9 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -644,8 +644,7 @@ function CharacteristicSection(id::Integer, s_entry::Real, section::Dict, v_limi :s_exit => section[:s_end], # last position (in m) :r_path => section[:f_Rp], # path resistance (in ‰) :v_limit => v_limit, # speed limit (in m/s) - # initializing :v_entry, :v_peak and :v_exit with :v_limit - :v_peak => v_limit, # maximum reachable speed (in m/s) + # initializing :v_entry and :v_exit with :v_limit :v_entry => v_limit, # maximum entry speed (in m/s) :v_exit => v_limit) # maximum exit speed (in m/s) From 6af091235962fabb6133750bf6491819d1365306 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 17 Aug 2022 12:18:27 +0200 Subject: [PATCH 04/14] Rename 'current speed limit' to 'lowest speed limit' --- src/behavior.jl | 78 ++++++++++++++++++++++++------------------------- src/calc.jl | 12 +++++--- 2 files changed, 47 insertions(+), 43 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index 5193894..a5e2194 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -52,7 +52,7 @@ function addBreakFreeSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags: stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0 stateFlags[:previousSpeedLimitReached] = false stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_limit] - stateFlags[:error] = !(stateFlags[:endOfCSReached] || stateFlags[:brakingStartReached] || stateFlags[:tractionDeficit] || stateFlags[:previousSpeedLimitReached] || stateFlags[:speedLimitReached]) + stateFlags[:error] = drivingCourse[end][:v] > CS[:v_limit] || drivingCourse[end][:s] > CS[:s_exit] return (CS, drivingCourse, stateFlags) end #function addBreakFreeSection! @@ -61,7 +61,7 @@ end #function addBreakFreeSection! # Therefore it gets its previous driving course and the characteristic section and returns the characteristic section and driving course including the clearing section. function addClearingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) if stateFlags[:previousSpeedLimitReached] - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics] ignoreBraking = true @@ -71,7 +71,7 @@ function addClearingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) end - s_clearing = min(CS[:s_exit]-drivingCourse[end][:s]-s_braking, currentSpeedLimit[:s_end] - drivingCourse[end][:s]) + s_clearing = min(CS[:s_exit]-drivingCourse[end][:s]-s_braking, lowestSpeedLimit[:s_end] - drivingCourse[end][:s]) if s_clearing > 0.0 (CS, drivingCourse, stateFlags) = addCruisingSection!(CS, drivingCourse, stateFlags, s_clearing, settings, train, CSs, "clearing") calculateForces!(drivingCourse[end], CSs, CS[:id], "accelerating", train, settings.massModel) @@ -81,8 +81,8 @@ function addClearingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: error("ERROR: clearing <=0.0 although it has to be >0.0 in CS ",CS[:id]) end #stateFlags[:previousSpeedLimitReached] = false - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) - stateFlags[:previousSpeedLimitReached] = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= currentSpeedLimit[:v] + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + stateFlags[:previousSpeedLimitReached] = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] else stateFlags[:error] = true end @@ -118,8 +118,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla drivingMode = "accelerating" drivingCourse[end][:behavior] = drivingMode - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) - previousSpeedLimitReached = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= currentSpeedLimit[:v] + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + previousSpeedLimitReached = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] while !speedLimitReached && !endOfCSReached && tractionSurplus && !brakingStartReached && !previousSpeedLimitReached currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections @@ -132,9 +132,9 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end while !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached - if drivingCourse[end][:s] >= currentSpeedLimit[:s_end] + if drivingCourse[end][:s] >= lowestSpeedLimit[:s_end] # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. On the other hand the train cruises possibly a little to long - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) end # acceleration (in m/s^2): @@ -152,7 +152,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] speedLimitReached = drivingCourse[end][:v] >= CS[:v_limit] - previousSpeedLimitReached = currentSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > currentSpeedLimit[:v] || (drivingCourse[end][:v] == currentSpeedLimit[:v] && drivingCourse[end][:s] < currentSpeedLimit[:s_end])) + previousSpeedLimitReached = lowestSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > lowestSpeedLimit[:v] || (drivingCourse[end][:v] == lowestSpeedLimit[:v] && drivingCourse[end][:s] < lowestSpeedLimit[:s_end])) pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] # POIs include s_exit as well tractionSurplus = drivingCourse[end][:F_T] > drivingCourse[end][:F_R] end #while @@ -181,10 +181,10 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla currentStepSize = settings.stepSize / 10.0^cycle end - elseif drivingCourse[end][:v] > currentSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=",currentSpeedLimit[:v]) # for testing + elseif drivingCourse[end][:v] > lowestSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v]) # for testing if settings.stepVariable == :velocity - currentStepSize = currentSpeedLimit[:v] - drivingCourse[end-1][:v] + currentStepSize = lowestSpeedLimit[:v] - drivingCourse[end-1][:v] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -196,8 +196,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end break - elseif drivingCourse[end][:v] == currentSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_limitCurrent=",currentSpeedLimit[:v]) # for testing + elseif drivingCourse[end][:v] == lowestSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing break elseif drivingCourse[end][:s] == nextPointOfInterest[1] @@ -208,7 +208,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla break else - println("v=",drivingCourse[end][:v]," v_limit= ", CS[:v_limit] , " v_currentLimit=", currentSpeedLimit[:v]) + println("v=",drivingCourse[end][:v]," v_limit= ", CS[:v_limit] , " v_lowestLimit=", lowestSpeedLimit[:v]) println("s=" ,drivingCourse[end][:s]," s_exit=", CS[:s_exit], " s+s_braking=", drivingCourse[end][:s] +s_braking," nextPOI=",nextPointOfInterest[1]) println("F_T=",drivingCourse[end][:F_T] ," F_R=", drivingCourse[end][:F_R]) @@ -226,8 +226,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla tractionSurplus = true else # if the level of approximation is reached - if drivingCourse[end][:v] > currentSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=",currentSpeedLimit[:v], "with v_limit=",CS[:v_limit]) # for testing + if drivingCourse[end][:v] > lowestSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v], "with v_limit=",CS[:v_limit]) # for testing pop!(drivingCourse) # conditions for the next section @@ -252,8 +252,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla else if drivingCourse[end][:s] + s_braking == CS[:s_exit] testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," else case and there: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing - elseif drivingCourse[end][:v] == currentSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_limitCurrent=",currentSpeedLimit[:v]) # for testing + elseif drivingCourse[end][:v] == lowestSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing end end @@ -526,8 +526,8 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: stateFlags[:brakingStartReached] = brakingStartReached || drivingCourse[end][:s] + s_braking >= CS[:s_exit] stateFlags[:tractionDeficit] = tractionDeficit stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0.0 - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) - stateFlags[:previousSpeedLimitReached] = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= currentSpeedLimit[:v] + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + stateFlags[:previousSpeedLimitReached] = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] stateFlags[:error] = !(targetPositionReached || tractionDeficit || !(cruisingType == "clearing" || ((cruisingType == "downhillBraking") == resistingForceNegative))) return (CS, drivingCourse, stateFlags) @@ -559,7 +559,7 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag drivingCourse[end][:behavior] = drivingMode while tractionDeficit && !targetSpeedReached && !endOfCSReached && !brakingStartReached - currentStepSize=settings.stepSize # initialize the step size that can be reduced near intersections + currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] @@ -710,8 +710,8 @@ end #function addDiminishingSection! function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) # conditions for coasting section - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) - previousSpeedLimitReached = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] > currentSpeedLimit[:v] + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + previousSpeedLimitReached = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] > lowestSpeedLimit[:v] speedLimitReached = drivingCourse[end][:v] > CS[:v_limit] targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || previousSpeedLimitReached || speedLimitReached endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached] @@ -725,15 +725,15 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: drivingCourse[end][:behavior] = drivingMode while !targetSpeedReached && !endOfCSReached && !brakingStartReached - currentStepSize=settings.stepSize # initialize the step size that can be reduced near intersections + currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections nextPointOfInterest[1] = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while !targetSpeedReached && !brakingStartReached && !pointOfInterestReached - if drivingCourse[end][:s] >= currentSpeedLimit[:s_end] + if drivingCourse[end][:s] >= lowestSpeedLimit[:s_end] # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) end # traction effort and resisting forces (in N): @@ -750,7 +750,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) brakingStartReached = drivingCourse[end][:s] + s_braking >= CS[:s_exit] pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] - targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || drivingCourse[end][:v] > CS[:v_limit] || currentSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > currentSpeedLimit[:v] || (drivingCourse[end][:v] == currentSpeedLimit[:v] && drivingCourse[end][:s] < currentSpeedLimit[:s_end])) + targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || drivingCourse[end][:v] > CS[:v_limit] || lowestSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > lowestSpeedLimit[:v] || (drivingCourse[end][:v] == lowestSpeedLimit[:v] && drivingCourse[end][:s] < lowestSpeedLimit[:s_end])) end # while testFlag = false @@ -777,10 +777,10 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: currentStepSize = settings.stepSize / 10.0^cycle end - elseif drivingCourse[end][:v] > currentSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," > v_limitCurrent=", currentSpeedLimit[:v]) # for testing + elseif drivingCourse[end][:v] > lowestSpeedLimit[:v] + testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v]) # for testing if settings.stepVariable == :velocity - currentStepSize = currentSpeedLimit[:v] - drivingCourse[end-1][:v] + currentStepSize = lowestSpeedLimit[:v] - drivingCourse[end-1][:v] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -825,14 +825,14 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: pointOfInterestReached = false targetSpeedReached = false - elseif drivingCourse[end][:v] > currentSpeedLimit[:v] # if the train gets to fast it has to brake to hold the velocity limit + elseif drivingCourse[end][:v] > lowestSpeedLimit[:v] # if the train gets to fast it has to brake to hold the velocity limit # delete last support point because it went to far pop!(drivingCourse) # conditions for the next for cycle brakingStartReached = false pointOfInterestReached = false - if currentSpeedLimit[:v] != CS[:v_limit] + if lowestSpeedLimit[:v] != CS[:v_limit] previousSpeedLimitReached = true else speedLimitReached = true @@ -1000,8 +1000,8 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D end # else: return the characteristic section without a braking section # set state flags - currentSpeedLimit = getCurrentSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) - stateFlags[:previousSpeedLimitReached] = currentSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= currentSpeedLimit[:v] + lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + stateFlags[:previousSpeedLimitReached] = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_exit] stateFlags[:endOfCSReached] = endOfCSReached stateFlags[:error] = !(endOfCSReached) @@ -1028,9 +1028,9 @@ end #function addHalt! function recalculateLastBrakingPoint!(drivingCourse, s_target, v_target) currentPoint = drivingCourse[end] previousPoint = drivingCourse[end-1] - # set s and v - currentPoint[:s] = s_target # position (in m) - currentPoint[:v] = v_target # velocity (in m/s) + # set s and v + currentPoint[:s] = s_target # position (in m) + currentPoint[:v] = v_target # velocity (in m/s) # calculate other values previousPoint[:a] = brakingAcceleration(previousPoint[:v], currentPoint[:v], currentPoint[:s]-previousPoint[:s]) diff --git a/src/calc.jl b/src/calc.jl index c97d744..d69e703 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -44,6 +44,10 @@ function calculateMinimumRunningTime!(CSs::Vector{Dict}, settings::Settings, tra # determine the behavior sections for this characteristic section. It has to be at least one of those BS: "breakFree", "clearing", "accelerating", "cruising", "diminishing", "coasting", "braking" or "halt") while !stateFlags[:endOfCSReached] # s < s_exit + if stateFlags[:error] + error("ERROR in calc in CS",CS[:id],": BS=",drivingCourse[end][:behavior]," s=",drivingCourse[end][:s]," s_braking=",s_braking," v_limit=",CS[:v_limit]," v=",drivingCourse[end][:v]," v_exit=",CS[:v_exit]," with the flags: endOfCS: ",stateFlags[:endOfCSReached]," brakingStart: ",stateFlags[:brakingStartReached]," F_T drivingCourse[end][:F_R] && drivingCourse[end][:v] == 0.0 @@ -287,7 +291,7 @@ end #function moveAStep """ # if the rear of the train is still located in a former characteristic section it has to be checked if its speed limit can be kept """ -function getCurrentSpeedLimit(CSs::Vector{Dict}, csWithTrainHeadId::Integer, s::Real, trainLength::Real) +function getLowestSpeedLimit(CSs::Vector{Dict}, csWithTrainHeadId::Integer, s::Real, trainLength::Real) v_limit = CSs[csWithTrainHeadId][:v_limit] s_exit = CSs[csWithTrainHeadId][:s_exit] if csWithTrainHeadId > 1 && s -trainLength < CSs[csWithTrainHeadId][:s_entry] @@ -300,9 +304,9 @@ function getCurrentSpeedLimit(CSs::Vector{Dict}, csWithTrainHeadId::Integer, s:: formerCsId = formerCsId -1 end end - currentSpeedLimit = Dict(:v => v_limit, :s_end => s_exit + trainLength) - return currentSpeedLimit -end #function getCurrentSpeedLimit + lowestSpeedLimit = Dict(:v => v_limit, :s_end => s_exit + trainLength) + return lowestSpeedLimit +end #function getLowestSpeedLimit """ From b421fbec5a02a029992928a6ee0c4a84de41681f Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 17 Aug 2022 12:58:53 +0200 Subject: [PATCH 05/14] Remove the redundant function 'secureAcceleratingBehavior' --- src/behavior.jl | 123 ++++-------------------------------------------- src/calc.jl | 1 - 2 files changed, 10 insertions(+), 114 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index a5e2194..65b923c 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -38,14 +38,8 @@ function addBreakFreeSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags: end # else: return the characteristic section without a breakFree section # determine state flags + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics] - s_braking = 0.0 - else - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end - - # reset state flags stateFlags[:endOfCSReached] = drivingCourse[end][:s] >= CS[:s_exit] stateFlags[:brakingStartReached] = drivingCourse[end][:s] +s_braking >= CS[:s_exit] stateFlags[:tractionDeficit] = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] # or add another flag for equal forces? @@ -62,14 +56,7 @@ end #function addBreakFreeSection! function addClearingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) if stateFlags[:previousSpeedLimitReached] lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) - - if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics] - ignoreBraking = true - s_braking = 0.0 - else - ignoreBraking = false - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) s_clearing = min(CS[:s_exit]-drivingCourse[end][:s]-s_braking, lowestSpeedLimit[:s_end] - drivingCourse[end][:s]) if s_clearing > 0.0 @@ -97,14 +84,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla -> CS = CSs[csId] =# calculateForces!(drivingCourse[end], CSs, CS[:id], "accelerating", train, settings.massModel) - - if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics] - ignoreBraking = true - s_braking = 0.0 - else - ignoreBraking = false - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) # conditions for the accelerating section endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached] @@ -127,10 +107,6 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation - if !ignoreBraking - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end - while !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached if drivingCourse[end][:s] >= lowestSpeedLimit[:s_end] # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. On the other hand the train cruises possibly a little to long @@ -147,9 +123,8 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) # conditions for the next while cycle - if !ignoreBraking - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) + brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] speedLimitReached = drivingCourse[end][:v] >= CS[:v_limit] previousSpeedLimitReached = lowestSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > lowestSpeedLimit[:v] || (drivingCourse[end][:v] == lowestSpeedLimit[:v] && drivingCourse[end][:s] < lowestSpeedLimit[:s_end])) @@ -302,13 +277,7 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: calculateForces!(drivingCourse[end], CSs, CS[:id], "braking", train, settings.massModel) end - if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics] - ignoreBraking = true - s_braking = 0.0 - else - ignoreBraking = false - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) # conditions for cruising section #s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) @@ -520,9 +489,7 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: # set state flags stateFlags[:endOfCSReached] = drivingCourse[end][:s] == CS[:s_exit] - if !ignoreBraking - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) stateFlags[:brakingStartReached] = brakingStartReached || drivingCourse[end][:s] + s_braking >= CS[:s_exit] stateFlags[:tractionDeficit] = tractionDeficit stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0.0 @@ -538,13 +505,7 @@ end #function addCruisingSection! function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) calculateForces!(drivingCourse[end], CSs, CS[:id], "diminishing", train, settings.massModel) - if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics] - ignoreBraking = true - s_braking = 0.0 - else - ignoreBraking = false - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) # conditions for diminishing section targetSpeedReached = drivingCourse[end][:v] <= 0.0 @@ -576,9 +537,8 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) # conditions for the next while cycle - if !ignoreBraking - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - end + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) + brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] targetSpeedReached = drivingCourse[end][:v] <= 0.0 @@ -1061,66 +1021,3 @@ function secureBrakingBehavior!(CSs::Vector{Dict}, a_braking::Real, approxLevel: end #while return CSs end #function secureBrakingBehavior! - -## define the intersection velocities between the characterisitc sections to secure accelerating behavior -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() - startingPoint[:i] = 1 - - previousCSv_exit = CSs[1][:v_entry] - for CS in CSs - CS[:v_entry] = min(CS[:v_entry], previousCSv_exit) - startingPoint[:s] = CS[:s_entry] - startingPoint[:v] = CS[:v_entry] - calculateForces!(startingPoint, CSs, CS[:id], "accelerating", train, settings.massModel) # traction effort and resisting forces (in N) - acceleratingCourse::Vector{Dict} = [startingPoint] # List of support points - - if CS[:v_entry] < CS[:v_limit] - # conditions for entering the accelerating phase - stateFlags = Dict(:endOfCSReached => false, - :brakingStartReached => false, - :tractionDeficit => false, - :resistingForceNegative => false, - :previousSpeedLimitReached => false, - :speedLimitReached => false, - :error => false, - :usedForDefiningCharacteristics => true) # because usedForDefiningCharacteristics == true the braking distance will be ignored during securing the accelerating phase - v_peak = CS[:v_entry] # maximum reachable speed in this CS (in m/s) - (CS, acceleratingCourse, stateFlags) = addBreakFreeSection!(CS, acceleratingCourse, stateFlags, settings, train, CSs) - while !stateFlags[:speedLimitReached] && !stateFlags[:endOfCSReached] - if !stateFlags[:tractionDeficit] - if !stateFlags[:previousSpeedLimitReached] - (CS, acceleratingCourse, stateFlags) = addAcceleratingSection!(CS, acceleratingCourse, stateFlags, settings, train, CSs) # this function changes the acceleratingCourse - - elseif stateFlags[:previousSpeedLimitReached] - (CS, acceleratingCourse, stateFlags) = addClearingSection!(CS, acceleratingCourse, stateFlags, settings, train, CSs) # this function is needed in case the train is not allowed to accelerate because of a previous speed limit - end - else - if settings.massModel == :mass_point || acceleratingCourse[end][:s] > CS[:s_entry] + train.length - break - else - (CS, acceleratingCourse, stateFlags) = addDiminishingSection!(CS, acceleratingCourse, stateFlags, settings, train, CSs) # this function is needed in case the resisitng forces are higher than the maximum possible tractive effort - end - end - v_peak = max(v_peak, acceleratingCourse[end][:v]) - end - - if v_peak == acceleratingCourse[end][:v] && CS[:v_limit] - acceleratingCourse[end][:v] < 1/(10^settings.approxLevel) - v_peak = CS[:v_limit] - else - v_peak = acceleratingCourse[end][:v] - end - CS[:v_exit] = min(CS[:v_exit], v_peak) - - #else CS[:v_entry] == CS[:v_limit] - # v_exit stays the same - end #if - - previousCSv_exit = CS[:v_exit] - end #for - - return CSs -end #function secureAcceleratingBehavior! diff --git a/src/calc.jl b/src/calc.jl index d69e703..d559658 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -340,7 +340,6 @@ function determineCharacteristics(path::Path, train::Train, settings::Settings) 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 From 548d46b6c45446a6ae4ac20cd2ea662edfc3c77d Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 17 Aug 2022 15:22:10 +0200 Subject: [PATCH 06/14] Remove the key :v_entry from CharacteristicSection dictionary --- src/behavior.jl | 12 ++++++------ src/calc.jl | 8 -------- src/constructors.jl | 4 +--- 3 files changed, 7 insertions(+), 17 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index 65b923c..a692bc1 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -1003,20 +1003,20 @@ end #function recalculateLastBrakingPoint ## define the intersection velocities between the characterisitc sections to secure braking behavior 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 + # limit the entry and exit velocities 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 + v_entryFollowing = 0.0 # the exit velocity of the last characteristic section is 0.0 m/s while csId >= 1 + # calculate the maximum possible entry velocity to define the previous section's maximum allowed exit velocity CS = CSs[csId] - CS[:v_exit] = min(CS[:v_limit], followingCSv_entry) + CS[:v_exit] = min(CS[:v_limit], v_entryFollowing) - v_entryMax = brakingStartVelocity(CS[:v_exit], a_braking, CS[:s_exit]-CS[:s_entry], approxLevel) + v_entry = brakingStartVelocity(CS[:v_exit], a_braking, CS[:s_exit]-CS[:s_entry], approxLevel) - CS[:v_entry] = min(CS[:v_limit], v_entryMax) + v_entryFollowing = min(CS[:v_limit], v_entry) - followingCSv_entry = CS[:v_entry] csId = csId - 1 end #while return CSs diff --git a/src/calc.jl b/src/calc.jl index d559658..474d5c0 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -21,14 +21,6 @@ function calculateMinimumRunningTime!(CSs::Vector{Dict}, settings::Settings, tra for csId in 1:length(CSs) CS = CSs[csId] - # 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 - if drivingCourse[end][:v] > CS[:v_entry] - println("ERROR: In CS", csId," the train run ends with v=",drivingCourse[end][:v]," and not with v_entry=",CS[:v_entry]) - end - # determine the different flags for switching between the states for creating moving phases s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) calculateForces!(drivingCourse[end], CSs, CS[:id], "default", train, settings.massModel) # tractive effort and resisting forces (in N) diff --git a/src/constructors.jl b/src/constructors.jl index c6ec5b9..f601efe 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -644,9 +644,7 @@ function CharacteristicSection(id::Integer, s_entry::Real, section::Dict, v_limi :s_exit => section[:s_end], # last position (in m) :r_path => section[:f_Rp], # path resistance (in ‰) :v_limit => v_limit, # speed limit (in m/s) - # initializing :v_entry and :v_exit with :v_limit - :v_entry => v_limit, # maximum entry speed (in m/s) - :v_exit => v_limit) # maximum exit speed (in m/s) + :v_exit => v_limit) # maximum exit speed (in m/s) initialized with v_limit # list of positions of every point of interest (POI) in this charateristic section for which support points should be calculated s_exit = characteristicSection[:s_exit] From 4d44674d21baedefd572768a9e92a543c0d21f02 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 17 Aug 2022 22:26:46 +0200 Subject: [PATCH 07/14] Remove key :id from CharacteristicSection dictionary --- src/behavior.jl | 238 ++++++++++++++++++++++---------------------- src/calc.jl | 142 +++++++++++++------------- src/constructors.jl | 15 ++- 3 files changed, 196 insertions(+), 199 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index a692bc1..046ba7c 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -7,7 +7,9 @@ ## This function calculates the support points of the breakFree section. # Therefore it gets its first support point and the characteristic section and returns the characteristic section including the behavior section for breakFree if needed. # Info: currently the values of the breakFree section will be calculated like in the accelerating section -function addBreakFreeSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) +function addBreakFreeSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train) + CS = CSs[csId] + # conditions for the break free section endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached] trainIsHalting = drivingCourse[end][:v] == 0.0 @@ -18,10 +20,10 @@ function addBreakFreeSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags: startingPoint = drivingCourse[end][:i] # traction effort and resisting forces (in N) - calculateForces!(drivingCourse[end], CSs, CS[:id], "accelerating", train, settings.massModel) # currently the tractive effort is calculated like in the accelerating section + calculateForces!(drivingCourse[end], CSs, csId, "accelerating", train, settings.massModel) # currently the tractive effort is calculated like in the accelerating section # calculate the breakFree section with calculating the accelerating section and just using the first step and removing the rest - try (CS, drivingCourse, stateFlags) = addAcceleratingSection!(CS, drivingCourse, stateFlags, settings, train, CSs) + try (drivingCourse, stateFlags) = addAcceleratingSection!(drivingCourse, stateFlags, CSs, csId, settings, train) catch(acceleratingError) println("This error happened during the break free phase that is using the accelerating function:") rethrow(acceleratingError) @@ -48,42 +50,41 @@ function addBreakFreeSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags: stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_limit] stateFlags[:error] = drivingCourse[end][:v] > CS[:v_limit] || drivingCourse[end][:s] > CS[:s_exit] - return (CS, drivingCourse, stateFlags) + return (drivingCourse, stateFlags) end #function addBreakFreeSection! ## This function calculates the support points of the clearing section. # Therefore it gets its previous driving course and the characteristic section and returns the characteristic section and driving course including the clearing section. -function addClearingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) +function addClearingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train) + CS = CSs[csId] + if stateFlags[:previousSpeedLimitReached] - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) s_clearing = min(CS[:s_exit]-drivingCourse[end][:s]-s_braking, lowestSpeedLimit[:s_end] - drivingCourse[end][:s]) if s_clearing > 0.0 - (CS, drivingCourse, stateFlags) = addCruisingSection!(CS, drivingCourse, stateFlags, s_clearing, settings, train, CSs, "clearing") - calculateForces!(drivingCourse[end], CSs, CS[:id], "accelerating", train, settings.massModel) - # stateFlags[:brakingStartReached] = brakingStartReached - # stateFlags[:endOfCSReached] = stateFlags[:endOfCSReached] || drivingCourse[end][:s] == CS[:s_exit] + (drivingCourse, stateFlags) = addCruisingSection!(drivingCourse, stateFlags, CSs, csId, settings, train, "clearing", s_clearing) + calculateForces!(drivingCourse[end], CSs, csId, "accelerating", train, settings.massModel) else - error("ERROR: clearing <=0.0 although it has to be >0.0 in CS ",CS[:id]) + error("ERROR: clearing <=0.0 although it has to be >0.0 in CS ",csId) end #stateFlags[:previousSpeedLimitReached] = false - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) stateFlags[:previousSpeedLimitReached] = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] else stateFlags[:error] = true end - return (CS, drivingCourse, stateFlags) + return (drivingCourse, stateFlags) 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}) - #= TODO: instead of CS just give csId? - -> CS = CSs[csId] =# +function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train) + CS = CSs[csId] - calculateForces!(drivingCourse[end], CSs, CS[:id], "accelerating", train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, "accelerating", train, settings.massModel) s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) # conditions for the accelerating section @@ -98,7 +99,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla drivingMode = "accelerating" drivingCourse[end][:behavior] = drivingMode - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) previousSpeedLimitReached = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] while !speedLimitReached && !endOfCSReached && tractionSurplus && !brakingStartReached && !previousSpeedLimitReached @@ -110,17 +111,17 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla while !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached if drivingCourse[end][:s] >= lowestSpeedLimit[:s_end] # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. On the other hand the train cruises possibly a little to long - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) end # acceleration (in m/s^2): drivingCourse[end][:a] = acceleration(drivingCourse[end][:F_T], drivingCourse[end][:F_R], train.m_train_full, train.ξ_train) # create the next support point - push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, CS[:id])) + push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) drivingCourse[end][:behavior] = drivingMode - calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, drivingMode, train, settings.massModel) # conditions for the next while cycle s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) @@ -132,7 +133,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla tractionSurplus = drivingCourse[end][:F_T] > drivingCourse[end][:F_R] end #while - if CS[:id]==0 + if csId==0 testFlag = true else testFlag = false # for testing @@ -141,15 +142,15 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla # check which limit was reached and adjust the currentStepSize for the next cycle if cycle < settings.approxLevel+1 if drivingCourse[end][:F_T] <= drivingCourse[end][:F_R] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," <= F_R=",drivingCourse[end][:F_R]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," <= F_R=",drivingCourse[end][:F_R]) # for testing currentStepSize = settings.stepSize / 10.0^cycle elseif s_braking > 0.0 && drivingCourse[end][:s] + s_braking > CS[:s_exit] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing currentStepSize = settings.stepSize / 10.0^cycle elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[1]) # for testing if settings.stepVariable == :distance currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] else @@ -157,7 +158,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end elseif drivingCourse[end][:v] > lowestSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v]) # for testing if settings.stepVariable == :velocity currentStepSize = lowestSpeedLimit[:v] - drivingCourse[end-1][:v] else @@ -165,18 +166,18 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end elseif drivingCourse[end][:s] + s_braking == CS[:s_exit] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing if s_braking == 0.0 endOfCSReached = true end break elseif drivingCourse[end][:v] == lowestSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing break elseif drivingCourse[end][:s] == nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[1]) # for testing if nextPointOfInterest[1] == CS[:s_exit] endOfCSReached = true end @@ -187,7 +188,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla println("s=" ,drivingCourse[end][:s]," s_exit=", CS[:s_exit], " s+s_braking=", drivingCourse[end][:s] +s_braking," nextPOI=",nextPointOfInterest[1]) println("F_T=",drivingCourse[end][:F_T] ," F_R=", drivingCourse[end][:F_R]) - error("ERROR at accelerating section: With the step variable ",settings.stepVariable," the while loop will be left although v lowestSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v], "with v_limit=",CS[:v_limit]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v], "with v_limit=",CS[:v_limit]) # for testing pop!(drivingCourse) # conditions for the next section brakingStartReached = false elseif drivingCourse[end][:s] + s_braking > CS[:s_exit] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing if s_braking > 0.0 pop!(drivingCourse) @@ -218,17 +219,17 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla end elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest elseif drivingCourse[end][:F_T] <= drivingCourse[end][:F_R] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," <= F_R=",drivingCourse[end][:F_R]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," <= F_R=",drivingCourse[end][:F_R]) # for testing else if drivingCourse[end][:s] + s_braking == CS[:s_exit] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," else case and there: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," else case and there: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing elseif drivingCourse[end][:v] == lowestSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing + testFlag && println("in CS",csId," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing end end @@ -260,21 +261,23 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla stateFlags[:speedLimitReached] = speedLimitReached stateFlags[:error] = !(endOfCSReached || brakingStartReached || stateFlags[:tractionDeficit] || previousSpeedLimitReached || speedLimitReached) - return (CS, drivingCourse, stateFlags) + return (drivingCourse, stateFlags) end #function addAcceleratingSection! ## This function calculates the support points of the cruising section. # Therefore it gets its first support point and the characteristic section and returns the characteristic section including the behavior section for cruising if needed. -function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, s_cruising::Real, settings::Settings, train::Train, CSs::Vector{Dict}, cruisingType::String) +function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train, cruisingType::String, s_cruising::Real) + CS = CSs[csId] + trainIsClearing = cruisingType == "clearing" trainIsBrakingDownhill = cruisingType == "downhillBraking" # traction effort and resisting forces (in N) if !trainIsBrakingDownhill # TODO: or just give drivingMode instead of "cruising"/"braking"? - calculateForces!(drivingCourse[end], CSs, CS[:id], "cruising", train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, "cruising", train, settings.massModel) else - calculateForces!(drivingCourse[end], CSs, CS[:id], "braking", train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, "braking", train, settings.massModel) end s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) @@ -296,12 +299,12 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: # traction effort and resisting forces (in N) if !trainIsBrakingDownhill - calculateForces!(drivingCourse[end], CSs, CS[:id], "cruising", train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, "cruising", train, settings.massModel) else - calculateForces!(drivingCourse[end], CSs, CS[:id], "braking", train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, "braking", train, settings.massModel) end - if settings.massModel == :homogeneous_strip && CS[:id] > 1 + if settings.massModel == :homogeneous_strip && csId > 1 # conditions for cruising section trainInPreviousCS = drivingCourse[end][:s] < CS[:s_entry] + train.length targetPositionReached = drivingCourse[end][:s] >= targetPosition @@ -331,20 +334,14 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: # create the next support point if settings.stepVariable == :distance || settings.stepVariable == time - push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, CS[:id])) + push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) else - push!(drivingCourse, moveAStep(drivingCourse[end], position, train.length/(10.0^cycle), CS[:id])) # TODO which step size should be used? + push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, train.length/(10.0^cycle), csId)) # TODO which step size should be used? end drivingCourse[end][:behavior] = drivingMode # traction effort and resisting forces (in N) - calculateForces!(drivingCourse[end], CSs, CS[:id], "default", train, settings.massModel) -# calculateForces!(drivingCourse[end], CSs, CS[:id], "cruising", train, settings.massModel) - #if !trainIsBrakingDownhill - # calculateForces!(drivingCourse[end], CSs, CS[:id], "cruising", train, settings.massModel) - #else - # calculateForces!(drivingCourse[end], CSs, CS[:id], "braking", train, settings.massModel) - #end + calculateForces!(drivingCourse[end], CSs, csId, "default", train, settings.massModel) # conditions for the next while cycle pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] # POIs include s_exit as well @@ -372,7 +369,7 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: currentStepSize = settings.stepSize / 10.0^cycle end - elseif drivingCourse[end][:s] > targetPosition # TODO also the following? drivingCourse[end][:s] > CSs[CS[:id]][:s_entry] + train.length)) + elseif drivingCourse[end][:s] > targetPosition # TODO also the following? drivingCourse[end][:s] > CS[:s_entry] + train.length)) if settings.stepVariable == :distance currentStepSize = targetPosition - drivingCourse[end-1][:s] else @@ -392,7 +389,7 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: break else - error("ERROR at cruising section: With the step variable ",settings.stepVariable," the while loop will be left although the if cases don't apply in CS",CS[:id]," with s=" ,drivingCourse[end][:s]," m and v=",drivingCourse[end][:v]," m/s") + error("ERROR at cruising section: With the step variable ",settings.stepVariable," the while loop will be left although the if cases don't apply in CS",csId," with s=" ,drivingCourse[end][:s]," m and v=",drivingCourse[end][:v]," m/s") end # delete last support point for recalculating the last step with reduced step size @@ -442,14 +439,12 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: resistingForceNegative = drivingCourse[end][:F_R] < 0.0 while !targetPositionReached && !tractionDeficit && (trainIsClearing || (trainIsBrakingDownhill == resistingForceNegative)) # while clearing tractive or braking force can be used - # 03/09 old: while drivingCourse[end][:s] < targetPosition && drivingCourse[end][:F_T] >= drivingCourse[end][:F_R] nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) if nextPointOfInterest[1] > targetPosition nextPointOfInterest = [targetPosition, ""] end # tractive effort (in N): -#03/25 drivingCourse[end][:F_T] = min(drivingCourse[end][:F_T], max(0.0, drivingCourse[end][:F_R])) if !trainIsBrakingDownhill drivingCourse[end][:F_T] = min(drivingCourse[end][:F_T], max(0.0, drivingCourse[end][:F_R])) else @@ -465,19 +460,14 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: s_cruisingRemaining = min(nextPointOfInterest[1] -drivingCourse[end][:s], targetPosition -drivingCourse[end][:s]) # create the next support point - push!(drivingCourse, moveAStep(drivingCourse[end], :distance, s_cruisingRemaining, CS[:id])) + push!(drivingCourse, moveAStep(drivingCourse[end], :distance, s_cruisingRemaining, csId)) drivingCourse[end][:behavior] = drivingMode if drivingCourse[end][:s] == nextPointOfInterest[1] drivingCourse[end][:label] = nextPointOfInterest[2] end - calculateForces!(drivingCourse[end], CSs, CS[:id], "default", train, settings.massModel) -# calculateForces!(drivingCourse[end], CSs, CS[:id], "cruising", train, settings.massModel) - #if !trainIsBrakingDownhill - # calculateForces!(drivingCourse[end], CSs, CS[:id], "cruising", train, settings.massModel) - #else - # calculateForces!(drivingCourse[end], CSs, CS[:id], "braking", train, settings.massModel) - #end + calculateForces!(drivingCourse[end], CSs, csId, "default", train, settings.massModel) + # conditions for the next while cycle targetPositionReached = drivingCourse[end][:s] >= targetPosition @@ -493,17 +483,19 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: stateFlags[:brakingStartReached] = brakingStartReached || drivingCourse[end][:s] + s_braking >= CS[:s_exit] stateFlags[:tractionDeficit] = tractionDeficit stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0.0 - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) stateFlags[:previousSpeedLimitReached] = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] stateFlags[:error] = !(targetPositionReached || tractionDeficit || !(cruisingType == "clearing" || ((cruisingType == "downhillBraking") == resistingForceNegative))) - return (CS, drivingCourse, stateFlags) + return (drivingCourse, stateFlags) end #function addCruisingSection! ## This function calculates the support points for diminishing run when using maximum tractive effort and still getting slower -function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) - calculateForces!(drivingCourse[end], CSs, CS[:id], "diminishing", train, settings.massModel) +function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train) + CS = CSs[csId] + + calculateForces!(drivingCourse[end], CSs, csId, "diminishing", train, settings.massModel) s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) @@ -531,10 +523,10 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag drivingCourse[end][:a] = acceleration(drivingCourse[end][:F_T], drivingCourse[end][:F_R], train.m_train_full, train.ξ_train) # create the next support point - push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, CS[:id])) + push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) drivingCourse[end][:behavior] = drivingMode - calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, drivingMode, train, settings.massModel) # conditions for the next while cycle s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) @@ -546,7 +538,7 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag endOfCSReached = drivingCourse[end][:s] == CS[:s_exit] end #while - if CS[:id]==0 + if csId==0 testFlag = true else testFlag = false # for testing @@ -561,15 +553,15 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag currentStepSize = settings.stepSize / 10.0^cycle # end elseif drivingCourse[end][:F_T] > drivingCourse[end][:F_R] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," > F_R=",drivingCourse[end][:F_R]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," > F_R=",drivingCourse[end][:F_R]) # for testing currentStepSize = settings.stepSize / 10.0^cycle elseif s_braking > 0.0 && drivingCourse[end][:s] + s_braking > CS[:s_exit] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing currentStepSize = settings.stepSize / 10.0^cycle elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[1]) # for testing if settings.stepVariable == :distance currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] else @@ -577,24 +569,24 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag end elseif drivingCourse[end][:s] + s_braking == CS[:s_exit] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing break elseif drivingCourse[end][:s] == nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[1]) # for testing break elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," == F_R=",drivingCourse[end][:F_R]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," == F_R=",drivingCourse[end][:F_R]) # for testing break elseif drivingCourse[end][:v] == 0.0 - error("ERROR: The train stops during diminishing run in CS",CS[:id]," at position s=",drivingCourse[end][:s]," m because the maximum tractive effort is lower than the resistant forces.", + error("ERROR: The train stops during diminishing run in CS",csId," at position s=",drivingCourse[end][:s]," m because the maximum tractive effort is lower than the resistant forces.", " Before the stop the last point has the values s=",drivingCourse[end-1][:s]," m v=",drivingCourse[end-1][:v]," m/s a=",drivingCourse[end-1][:a]," m/s^2", " F_T=",drivingCourse[end-1][:F_T]," N R_traction=",drivingCourse[end-1][:R_traction]," N R_wagons=",drivingCourse[end-1][:R_wagons]," N R_path=",drivingCourse[end-1][:R_path]," N.") else - error("ERROR during diminishing run: With the step variable ",settings.stepVariable," the while loop will be left although s+s_braking0.0 in CS",CS[:id]," with s=" ,drivingCourse[end][:s]," m and v=",drivingCourse[end][:v]," m/s") + error("ERROR during diminishing run: With the step variable ",settings.stepVariable," the while loop will be left although s+s_braking0.0 in CS",csId," with s=" ,drivingCourse[end][:s]," m and v=",drivingCourse[end][:v]," m/s") end # delete last support point for recalculating the last step with reduced step size pop!(drivingCourse) @@ -608,13 +600,13 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag else # if the level of approximation is reached if drivingCourse[end][:v] <= 0.0 - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: v=", drivingCourse[end][:v]," <= 0.0") # for testing - error("ERROR: The train stops during diminishing run in CS",CS[:id]," because the maximum tractive effort is lower than the resistant forces.", + testFlag && println("in CS",csId," diminishing cycle",cycle," case: v=", drivingCourse[end][:v]," <= 0.0") # for testing + error("ERROR: The train stops during diminishing run in CS",csId," because the maximum tractive effort is lower than the resistant forces.", " Before the stop the last point has the values s=",drivingCourse[end-1][:s]," m v=",drivingCourse[end-1][:v]," m/s a=",drivingCourse[end-1][:a]," m/s^2", " F_T=",drivingCourse[end-1][:F_T]," N R_traction=",drivingCourse[end-1][:R_traction]," N R_wagons=",drivingCourse[end-1][:R_wagons]," N R_path=",drivingCourse[end-1][:R_path]," N.") elseif s_braking > 0.0 && drivingCourse[end][:s] + s_braking > CS[:s_exit] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing pop!(drivingCourse) pointOfInterestReached = false @@ -623,15 +615,15 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag endOfCSReached = false elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest elseif drivingCourse[end][:F_T] >= drivingCourse[end][:F_R] - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," >= F_R=", drivingCourse[end][:F_R]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," >= F_R=", drivingCourse[end][:F_R]) # for testing break else - testFlag && println("in CS",CS[:id]," diminishing cycle",cycle," case: else with v=", drivingCourse[end][:v]," > 0.0 and F_T=", drivingCourse[end][:F_T]," <= F_R=", drivingCourse[end][:F_R]) # for testing + testFlag && println("in CS",csId," diminishing cycle",cycle," case: else with v=", drivingCourse[end][:v]," > 0.0 and F_T=", drivingCourse[end][:F_T]," <= F_R=", drivingCourse[end][:F_R]) # for testing #println(" and s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," <= s_exit=",CS[:s_exit]) # for testing #println(" and s=", drivingCourse[end][:s]," <= nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing @@ -661,16 +653,17 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_limit] stateFlags[:error] = !(endOfCSReached || brakingStartReached || !tractionDeficit) - return (CS, drivingCourse, stateFlags) + return (drivingCourse, stateFlags) end #function addDiminishingSection! ## This function calculates the support points of the coasting section. # Therefore it gets its previous driving course and the characteristic section and returns the characteristic section and driving course including the coasting section -function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::Dict, settings::Settings, train::Train, CSs::Vector{Dict}) +function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train) + CS = CSs[csId] # conditions for coasting section - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) previousSpeedLimitReached = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] > lowestSpeedLimit[:v] speedLimitReached = drivingCourse[end][:v] > CS[:v_limit] targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || previousSpeedLimitReached || speedLimitReached @@ -693,17 +686,17 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: while !targetSpeedReached && !brakingStartReached && !pointOfInterestReached if drivingCourse[end][:s] >= lowestSpeedLimit[:s_end] # could be asked after creating an support point. This way here prevents even a minimal exceedance of speed limit. - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) end # traction effort and resisting forces (in N): - calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, drivingMode, train, settings.massModel) # acceleration (in m/s^2): drivingCourse[end][:a] = acceleration(drivingCourse[end][:F_T], drivingCourse[end][:F_R], train.m_train_full, train.ξ_train) # create the next support point - push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, CS[:id])) + push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) drivingCourse[end][:behavior] = drivingMode # conditions for the next while cycle @@ -718,11 +711,11 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: # check which limit was reached and adjust the currentStepSize for the next cycle if cycle < settings.approxLevel+1 if drivingCourse[end][:s] + s_braking > CS[:s_exit] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing currentStepSize = settings.stepSize / 10.0^cycle elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing if settings.stepVariable == :distance currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] else @@ -730,7 +723,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: end elseif drivingCourse[end][:v] < CS[:v_exit] # TODO: if accelereation and coasting functions will be combined this case is only for coasting - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," < v_exit=", CS[:v_exit]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," < v_exit=", CS[:v_exit]) # for testing if settings.stepVariable == :velocity currentStepSize = drivingCourse[end-1][:v] - CS[:v_exit] else @@ -738,7 +731,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: end elseif drivingCourse[end][:v] > lowestSpeedLimit[:v] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," > v_lowestLimit=", lowestSpeedLimit[:v]) # for testing if settings.stepVariable == :velocity currentStepSize = lowestSpeedLimit[:v] - drivingCourse[end-1][:v] else @@ -746,20 +739,20 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:: end elseif drivingCourse[end][:s] + s_braking == CS[:s_exit] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing break elseif drivingCourse[end][:v] == CS[:v_exit] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," == v_exit=", CS[:v_exit]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," == v_exit=", CS[:v_exit]) # for testing break elseif drivingCourse[end][:s] == nextPointOfInterest[1] - testFlag && println("in CS",CS[:id]," coasting cycle",cycle," case: s =", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + testFlag && println("in CS",csId," coasting cycle",cycle," case: s =", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing break else # TODO: not needed. just for testing - error("ERROR at coasting until braking section: With the step variable ",settings.stepVariable," the while loop will be left although v= CS[:s_exit] || stateFlags[:endOfCSReached] @@ -847,7 +842,7 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D while !targetSpeedReached && !endOfCSReached && !pointOfInterestReached # 03/09 old: while drivingCourse[end][:v] > CS[:v_exit] && !targetSpeedReached && drivingCourse[end][:s] < CS[:s_exit] && drivingCourse[end][:s] < nextPointOfInterest[1] # traction effort and resisting forces (in N): - calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, drivingMode, train, settings.massModel) # acceleration (in m/s^2): drivingCourse[end][:a] = train.a_braking @@ -861,7 +856,7 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) else # create the next support point - push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, CS[:id])) + push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) drivingCourse[end][:behavior] = drivingMode end #println(drivingCourse[end][:i],". s=",drivingCourse[end][:s]," s_exit=", CS[:s_exit]," v_exit=", CS[:v_exit]," v=",drivingCourse[end][:v]) @@ -881,25 +876,27 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D else currentStepSize = settings.stepSize / 10.0^cycle end + elseif drivingCourse[end][:s] > nextPointOfInterest[1] if settings.stepVariable == :distance currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] else currentStepSize = settings.stepSize / 10.0^cycle end + elseif drivingCourse[end][:v] == CS[:v_exit] && drivingCourse[end][:s] == CS[:s_exit] break + elseif drivingCourse[end][:v] == CS[:v_exit] recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) endOfCSReached = true - # println(" with a=", drivingCourse[end-1][:a]) # for testing break + elseif drivingCourse[end][:s] == CS[:s_exit] - # println("during braking section in CS",CS[:id],": rounding v down from ", drivingCourse[end][:v] ," to ", CS[:v_exit]) # for testing recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) targetSpeedReached = true - # println(" with a=", drivingCourse[end-1][:a]) # for testing break + elseif drivingCourse[end][:s] == nextPointOfInterest[1] break end @@ -915,13 +912,13 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D else # if the level of approximation is reached if drivingCourse[end][:v] < 0.0 # TODO: drivingCourse[end][:v] < CS[:v_exit] should be enough - # reset last point with setting v=v_exit - # println("during braking section in CS",CS[:id],": rounding v up from ", drivingCourse[end][:v] ," to ", CS[:v_exit]) # for testing + # reset last point with setting v=v_exit. still possible with v_exit now meaning v_exitMax? + # println("during braking section in CS",csId,": rounding v up from ", drivingCourse[end][:v] ," to ", CS[:v_exit]) # for testing recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], 0.0) endOfCSReached = true break elseif drivingCourse[end][:s] > CS[:s_exit] - # println("during braking section in CS",CS[:id],": rounding s down from ", drivingCourse[end][:s] ," to ", CS[:s_exit]) # for testing + # println("during braking section in CS",csId,": rounding s down from ", drivingCourse[end][:s] ," to ", CS[:s_exit]) # for testing # recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) drivingCourse[end][:s] = CS[:s_exit] break @@ -932,17 +929,17 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D break elseif drivingCourse[end][:v] < CS[:v_exit] # reset last point with setting v=v_exit - # println("during braking section in CS",CS[:id],": rounding s up from ", drivingCourse[end][:s] ," to ", CS[:s_exit]) # for testing + # println("during braking section in CS",csId,": rounding s up from ", drivingCourse[end][:s] ," to ", CS[:s_exit]) # for testing recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) endOfCSReached = true break elseif drivingCourse[end][:v] == CS[:v_exit] - # println("during braking section in CS",CS[:id],": rounding s up from ", drivingCourse[end][:s] ," to ", CS[:s_exit]) # for testing + # println("during braking section in CS",csId,": rounding s up from ", drivingCourse[end][:s] ," to ", CS[:s_exit]) # for testing recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) endOfCSReached = true break elseif drivingCourse[end][:s] == CS[:s_exit] - # println("during braking section in CS",CS[:id],": rounding v down from ", drivingCourse[end][:v] ," to ", CS[:v_exit]) # for testing + # println("during braking section in CS",csId,": rounding v down from ", drivingCourse[end][:v] ," to ", CS[:v_exit]) # for testing recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) targetSpeedReached = true break @@ -960,29 +957,30 @@ function addBrakingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::D end # else: return the characteristic section without a braking section # set state flags - lowestSpeedLimit = getLowestSpeedLimit(CSs, CS[:id], drivingCourse[end][:s], train.length) + lowestSpeedLimit = getLowestSpeedLimit(CSs, csId, drivingCourse[end][:s], train.length) stateFlags[:previousSpeedLimitReached] = lowestSpeedLimit[:v] != CS[:v_limit] && drivingCourse[end][:v] >= lowestSpeedLimit[:v] stateFlags[:speedLimitReached] = drivingCourse[end][:v] >= CS[:v_exit] stateFlags[:endOfCSReached] = endOfCSReached stateFlags[:error] = !(endOfCSReached) - calculateForces!(drivingCourse[end], CSs, CS[:id], "default", train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, "default", train, settings.massModel) stateFlags[:resistingForceNegative] = drivingCourse[end][:F_R] < 0 - return (CS, drivingCourse, stateFlags) + return (drivingCourse, stateFlags) end #function addBrakingSection! ## This function calculates the support point of the halt. # Therefore it gets its first support point and the characteristic section and returns the characteristic section including the halt if needed. -function addHalt!(CS::Dict, drivingCourse::Vector{Dict}, settings::Settings, train::Train, CSs::Vector{Dict}) +function addHalt!(drivingCourse::Vector{Dict}, CSs::Vector{Dict}, csId::Integer, settings::Settings, train::Train) + # CS = CSs[csId] # is not needed here if drivingCourse[end][:v] == 0.0 drivingMode = "halt" drivingCourse[end][:behavior] = drivingMode # traction effort and resisting forces (in N) - calculateForces!(drivingCourse[end], CSs, CS[:id], drivingMode, train, settings.massModel) + calculateForces!(drivingCourse[end], CSs, csId, drivingMode, train, settings.massModel) end # else: return the characteristic section without a halt section section - return (CS, drivingCourse) + return drivingCourse end #function addHalt! function recalculateLastBrakingPoint!(drivingCourse, s_target, v_target) @@ -996,7 +994,7 @@ function recalculateLastBrakingPoint!(drivingCourse, s_target, v_target) previousPoint[:a] = brakingAcceleration(previousPoint[:v], currentPoint[:v], currentPoint[:s]-previousPoint[:s]) # # TODO: just for testing # if previousPoint[:a]=0.0 -# println("Warning: a_braking gets to high in CS ",CS[:id], " with a=",previousPoint[:a] ," > ",train.a_braking) +# println("Warning: a_braking gets to high in CS ",csId, " with a=",previousPoint[:a] ," > ",train.a_braking) # end currentPoint[:t] = previousPoint[:t] + Δt_with_Δv(currentPoint[:v]-previousPoint[:v], previousPoint[:a]) # point in time (in s) end #function recalculateLastBrakingPoint diff --git a/src/calc.jl b/src/calc.jl index 474d5c0..e756332 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -23,89 +23,89 @@ function calculateMinimumRunningTime!(CSs::Vector{Dict}, settings::Settings, tra CS = CSs[csId] # determine the different flags for switching between the states for creating moving phases s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - calculateForces!(drivingCourse[end], CSs, CS[:id], "default", train, settings.massModel) # tractive effort and resisting forces (in N) + calculateForces!(drivingCourse[end], CSs, csId, "default", train, settings.massModel) # tractive effort and resisting forces (in N) previousSpeedLimitReached = false stateFlags = Dict(:endOfCSReached => drivingCourse[end][:s] > CS[:s_exit], :brakingStartReached => drivingCourse[end][:s] + s_braking == CS[:s_exit], :tractionDeficit => drivingCourse[end][:F_T] < drivingCourse[end][:F_R], # or add another flag for equal forces? :resistingForceNegative => drivingCourse[end][:F_R] < 0.0, - :previousSpeedLimitReached => false, #speedLimitReached, # check already at this position? + :previousSpeedLimitReached => false, :speedLimitReached => drivingCourse[end][:v] > CS[:v_limit], :error => false) - # determine the behavior sections for this characteristic section. It has to be at least one of those BS: "breakFree", "clearing", "accelerating", "cruising", "diminishing", "coasting", "braking" or "halt") - while !stateFlags[:endOfCSReached] # s < s_exit - if stateFlags[:error] - error("ERROR in calc in CS",CS[:id],": BS=",drivingCourse[end][:behavior]," s=",drivingCourse[end][:s]," s_braking=",s_braking," v_limit=",CS[:v_limit]," v=",drivingCourse[end][:v]," v_exit=",CS[:v_exit]," with the flags: endOfCS: ",stateFlags[:endOfCSReached]," brakingStart: ",stateFlags[:brakingStartReached]," F_T drivingCourse[end][:F_R] && drivingCourse[end][:v] == 0.0 - (CS, drivingCourse, stateFlags) = addBreakFreeSection!(CS, drivingCourse, stateFlags, settings, train, CSs) - - elseif stateFlags[:previousSpeedLimitReached] - (CS, drivingCourse, stateFlags) = addClearingSection!(CS, drivingCourse, stateFlags, settings, train, CSs) - - elseif drivingCourse[end][:F_T] > drivingCourse[end][:F_R] && !stateFlags[:speedLimitReached] - (CS, drivingCourse, stateFlags) = addAcceleratingSection!(CS, drivingCourse, stateFlags, settings, train, CSs) - - elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] && !stateFlags[:speedLimitReached] - # cruise only one step - if settings.stepVariable == :distance - s_cruising = settings.stepSize - elseif settings.stepVariable == time - s_cruising = Δs_with_Δt(settings.stepSize, drivingCourse[end][:a], drivingCourse[end][:v]) - elseif settings.stepVariable == velocity - s_cruising = train.length/(10.0) # TODO which step size should be used? - end - (CS, drivingCourse, stateFlags) = addCruisingSection!(CS, drivingCourse, stateFlags, s_cruising, settings, train, CSs, "cruising") - - elseif drivingCourse[end][:F_R] < 0 && stateFlags[:speedLimitReached] - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - s_cruising = CS[:s_exit] - drivingCourse[end][:s] - s_braking - - if s_cruising > 0.0 - (CS, drivingCourse, stateFlags) = addCruisingSection!(CS, drivingCourse, stateFlags, s_cruising, settings, train, CSs, "downhillBraking") - else - stateFlags[:brakingStartReached] = true - end - - elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] || stateFlags[:speedLimitReached] - s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) - s_cruising = CS[:s_exit] - drivingCourse[end][:s] - s_braking - - if s_cruising > 1/10^(settings.approxLevel) # TODO: define another minimum cruising length? - (CS, drivingCourse, stateFlags) = addCruisingSection!(CS, drivingCourse, stateFlags, s_cruising, settings, train, CSs, "cruising") - else - stateFlags[:brakingStartReached] = true - end - else - error() - end - elseif stateFlags[:tractionDeficit] - (CS, drivingCourse, stateFlags) = addDiminishingSection!(CS, drivingCourse, stateFlags, settings, train, CSs) - - else - error() + # determine the behavior sections for this characteristic section. It has to be at least one of those BS: "breakFree", "clearing", "accelerating", "cruising", "diminishing", "coasting", "braking" or "halt") + while !stateFlags[:endOfCSReached] # s < s_exit + if stateFlags[:error] + error("ERROR in calc in CS",csId,": BS=",drivingCourse[end][:behavior]," s=",drivingCourse[end][:s]," s_braking=",s_braking," v_limit=",CS[:v_limit]," v=",drivingCourse[end][:v]," v_exit=",CS[:v_exit]," with the flags: endOfCS: ",stateFlags[:endOfCSReached]," brakingStart: ",stateFlags[:brakingStartReached]," F_T drivingCourse[end][:F_R] && drivingCourse[end][:v] == 0.0 + (drivingCourse, stateFlags) = addBreakFreeSection!(drivingCourse, stateFlags, CSs, csId, settings, train) - # set state flag - stateFlags[:endOfCSReached] = true + elseif stateFlags[:previousSpeedLimitReached] + (drivingCourse, stateFlags) = addClearingSection!(drivingCourse, stateFlags, CSs, csId, settings, train) + + elseif drivingCourse[end][:F_T] > drivingCourse[end][:F_R] && !stateFlags[:speedLimitReached] + (drivingCourse, stateFlags) = addAcceleratingSection!(drivingCourse, stateFlags, CSs, csId, settings, train) + + elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] && !stateFlags[:speedLimitReached] + # cruise only one step + if settings.stepVariable == :distance + s_cruising = settings.stepSize + elseif settings.stepVariable == time + s_cruising = Δs_with_Δt(settings.stepSize, drivingCourse[end][:a], drivingCourse[end][:v]) + elseif settings.stepVariable == velocity + s_cruising = train.length/(10.0) # TODO which step size should be used? + end + (drivingCourse, stateFlags) = addCruisingSection!(drivingCourse, stateFlags, CSs, csId, settings, train, "cruising", s_cruising) + + elseif drivingCourse[end][:F_R] < 0 && stateFlags[:speedLimitReached] + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) + s_cruising = CS[:s_exit] - drivingCourse[end][:s] - s_braking + + if s_cruising > 0.0 + (drivingCourse, stateFlags) = addCruisingSection!(drivingCourse, stateFlags, CSs, csId, settings, train, "downhillBraking", s_cruising) + else + stateFlags[:brakingStartReached] = true + end + + elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] || stateFlags[:speedLimitReached] + s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) + s_cruising = CS[:s_exit] - drivingCourse[end][:s] - s_braking + + if s_cruising > 1/10^(settings.approxLevel) # TODO: define another minimum cruising length? + (drivingCourse, stateFlags) = addCruisingSection!(drivingCourse, stateFlags, CSs, csId, settings, train, "cruising", s_cruising) + else + stateFlags[:brakingStartReached] = true + end + else + error() + end + elseif stateFlags[:tractionDeficit] + (drivingCourse, stateFlags) = addDiminishingSection!(drivingCourse, stateFlags, CSs, csId, settings, train) + + else + error() + end + else#if !stateFlags[:endOfCSReached] # s < s_exit + (drivingCourse, stateFlags) = addBrakingSection!(drivingCourse, stateFlags, CSs, csId, settings, train) + #else + # error() + end + + if CS[:s_exit] - drivingCourse[end][:s] < 1/10^(settings.approxLevel) + drivingCourse[end][:s] = CS[:s_exit] # round s up to CS[:s_exit] + + # set state flag + stateFlags[:endOfCSReached] = true + end end - end - #if s == s_exit - # halt - #end + #if s == s_exit + # halt + #end # for testing: # TODO @@ -117,7 +117,7 @@ function calculateMinimumRunningTime!(CSs::Vector{Dict}, settings::Settings, tra end end #for - (CSs[end], drivingCourse) = addHalt!(CSs[end], drivingCourse, settings, train, CSs) + drivingCourse = addHalt!(drivingCourse, CSs, length(CSs), settings, train) return (CSs, drivingCourse) end #function calculateMinimumRunningTime diff --git a/src/constructors.jl b/src/constructors.jl index f601efe..2dc30cc 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -617,30 +617,29 @@ end #function Train() # outer constructor 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}() + CSs = Vector{Dict}() s_csStart = path.sections[1][:s_start] # first position (in m) - csId = 1 + #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, MS_poi)) + push!(CSs, CharacteristicSection(s_csStart, previousSection, min(previousSection[:v_limit], v_trainLimit), s_trainLength, MS_poi)) s_csStart = currentSection[:s_start] - csId = csId+1 + #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, MS_poi)) + push!(CSs, CharacteristicSection(s_csStart, path.sections[end], min(path.sections[end][:v_limit], v_trainLimit), s_trainLength, MS_poi)) 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}) +function CharacteristicSection(s_entry::Real, section::Dict, v_limit::Real, s_trainLength::Real, MS_poi::Vector{Tuple}) # Create and return a characteristic section dependent on the paths attributes - characteristicSection::Dict{Symbol, Any} = Dict(:id => id, # identifier - :s_entry => s_entry, # first position (in m) + characteristicSection::Dict{Symbol, Any} = Dict(:s_entry => s_entry, # first position (in m) :s_exit => section[:s_end], # last position (in m) :r_path => section[:f_Rp], # path resistance (in ‰) :v_limit => v_limit, # speed limit (in m/s) From 4a047f4cf2f8f858fa4b1f76d6bacd45083ec9c7 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 17 Aug 2022 22:30:32 +0200 Subject: [PATCH 08/14] Remove CharacteristicSections as return value from function 'calculateMinimumRunningTime' --- src/TrainRuns.jl | 2 +- src/calc.jl | 9 ++------- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/src/TrainRuns.jl b/src/TrainRuns.jl index 5cf5801..98882bb 100644 --- a/src/TrainRuns.jl +++ b/src/TrainRuns.jl @@ -50,7 +50,7 @@ function trainrun(train::Train, path::Path, settings=Settings()::Settings) # TODO settings.outputDetail == :verbose && println("The characteristics haven been determined.") # calculate the train run with the minimum running time - (characteristicSections, drivingCourse) = calculateMinimumRunningTime!(characteristicSections, settings, train) + 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 diff --git a/src/calc.jl b/src/calc.jl index e756332..0018e9b 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -7,12 +7,7 @@ # 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!(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 # TODO - +function calculateMinimumRunningTime(CSs::Vector{Dict}, settings::Settings, train::Train) startingPoint = SupportPoint() startingPoint[:i] = 1 startingPoint[:s] = CSs[1][:s_entry] @@ -119,7 +114,7 @@ function calculateMinimumRunningTime!(CSs::Vector{Dict}, settings::Settings, tra drivingCourse = addHalt!(drivingCourse, CSs, length(CSs), settings, train) - return (CSs, drivingCourse) + return drivingCourse end #function calculateMinimumRunningTime From 94839a28c079d65acaa19b6b031c85510862e8e3 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Thu, 18 Aug 2022 13:44:57 +0200 Subject: [PATCH 09/14] Remove key :i from SupportPoint dictionary --- src/behavior.jl | 6 ++---- src/calc.jl | 2 -- src/constructors.jl | 3 +-- 3 files changed, 3 insertions(+), 8 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index 046ba7c..10d3c88 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -17,7 +17,7 @@ function addBreakFreeSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs if trainIsHalting && !endOfCSReached drivingMode = "breakFree" drivingCourse[end][:behavior] = drivingMode - startingPoint = drivingCourse[end][:i] + startingPoint = length(drivingCourse) # traction effort and resisting forces (in N) calculateForces!(drivingCourse[end], CSs, csId, "accelerating", train, settings.massModel) # currently the tractive effort is calculated like in the accelerating section @@ -30,7 +30,7 @@ function addBreakFreeSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs end # delete every supportPoint except the first two - while drivingCourse[end][:i] > startingPoint +1 + while length(drivingCourse) > startingPoint +1 pop!(drivingCourse) end @@ -851,7 +851,6 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: if settings.stepVariable == :distance && ((drivingCourse[end][:v]/drivingCourse[end][:a])^2+2*currentStepSize/drivingCourse[end][:a])<0.0 || (drivingCourse[end][:v]^2+2*currentStepSize*drivingCourse[end][:a])<0.0 # create empty support point and set it for the values of s_exit and v_exit push!(drivingCourse, SupportPoint()) - drivingCourse[end][:i] = drivingCourse[end-1][:i]+1 drivingCourse[end][:behavior] = drivingMode recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) else @@ -859,7 +858,6 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) drivingCourse[end][:behavior] = drivingMode end - #println(drivingCourse[end][:i],". s=",drivingCourse[end][:s]," s_exit=", CS[:s_exit]," v_exit=", CS[:v_exit]," v=",drivingCourse[end][:v]) # conditions for the next while cycle pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] diff --git a/src/calc.jl b/src/calc.jl index 0018e9b..21ff56a 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -9,7 +9,6 @@ # calculate a train run focussing on using the minimum possible running time function calculateMinimumRunningTime(CSs::Vector{Dict}, settings::Settings, train::Train) startingPoint = SupportPoint() - startingPoint[:i] = 1 startingPoint[:s] = CSs[1][:s_entry] calculateForces!(startingPoint, CSs, 1, "default", train, settings.massModel) # traction effort and resisting forces (in N) drivingCourse::Vector{Dict} = [startingPoint] # List of support points @@ -223,7 +222,6 @@ function moveAStep(previousPoint::Dict, stepVariable::Symbol, stepSize::Real, cs # create the next support point newPoint = SupportPoint() - newPoint[:i] = previousPoint[:i]+1 # identifier # calculate s, t, v, E if stepVariable == :distance # distance step method diff --git a/src/constructors.jl b/src/constructors.jl index 2dc30cc..bbe6289 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -671,9 +671,8 @@ a SupportPoint is the smallest element of the driving course. One step of the st """ function SupportPoint() supportPoint = Dict( - :i => 0, # identifier and counter variable of the driving course :behavior => "", # type of behavior section the support point is part of - see BehaviorSection() - # a support point which is the last point of one behavior section and the first point of the next behavior section will be attached to the latter + # a support point which is the last point of one behavior section and the first point of the next behavior section will be attached to the latter :s => 0.0, # position (in m) :t => 0.0, # point in time (in s) :v => 0.0, # velocity (in m/s) From 8c286b0d2b626b56d5bd49d9ad0b5daf99d49b75 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Fri, 19 Aug 2022 19:51:02 +0200 Subject: [PATCH 10/14] Change type of a point of interest from Tuple to NamedTuple --- src/calc.jl | 9 ++++----- src/constructors.jl | 22 ++++++++++------------ src/output.jl | 2 +- 3 files changed, 15 insertions(+), 18 deletions(-) diff --git a/src/calc.jl b/src/calc.jl index 21ff56a..6f5f293 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -297,7 +297,7 @@ end #function getLowestSpeedLimit """ TODO """ -function getNextPointOfInterest(pointsOfInterest::Vector{Tuple}, s::Real) +function getNextPointOfInterest(pointsOfInterest::Vector{NamedTuple}, s::Real) for POI in pointsOfInterest if POI[1] > s return POI @@ -310,17 +310,16 @@ end #function getNextPointOfInterest ## 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) # 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[] + pointsOfInterest = NamedTuple[] 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]) ) + push!(pointsOfInterest, (s = s_poi, label = POI[:label]) ) end - sort!(pointsOfInterest, by = x -> x[1]) + sort!(pointsOfInterest, by = x -> x[:s]) end characteristicSections = CharacteristicSections(path, train.v_limit, train.length, pointsOfInterest) diff --git a/src/constructors.jl b/src/constructors.jl index bbe6289..3216467 100644 --- a/src/constructors.jl +++ b/src/constructors.jl @@ -614,7 +614,7 @@ function Train(file, type = :YAML) end #function Train() # outer constructor ## create the moving section's characteristic sections -function CharacteristicSections(path::Path, v_trainLimit::Real, s_trainLength::Real, MS_poi::Vector{Tuple}) +function CharacteristicSections(path::Path, v_trainLimit::Real, s_trainLength::Real, MS_poi::Vector{NamedTuple}) # create and return the characteristic sections of a moving section dependent on the paths attributes CSs = Vector{Dict}() @@ -636,8 +636,8 @@ function CharacteristicSections(path::Path, v_trainLimit::Real, s_trainLength::R 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(s_entry::Real, section::Dict, v_limit::Real, s_trainLength::Real, MS_poi::Vector{Tuple}) +## create a characteristic section for a path section. +function CharacteristicSection(s_entry::Real, section::Dict, v_limit::Real, s_trainLength::Real, MS_poi::Vector{NamedTuple}) # Create and return a characteristic section dependent on the paths attributes characteristicSection::Dict{Symbol, Any} = Dict(:s_entry => s_entry, # first position (in m) :s_exit => section[:s_end], # last position (in m) @@ -645,23 +645,21 @@ function CharacteristicSection(s_entry::Real, section::Dict, v_limit::Real, s_tr :v_limit => v_limit, # speed limit (in m/s) :v_exit => v_limit) # maximum exit speed (in m/s) initialized with v_limit - # list of positions of every point of interest (POI) in this charateristic section for which support points should be calculated + # get the list of positions of every point of interest (POI) in this charateristic section for which support points should be calculated from the list of the whole moving section's POI s_exit = characteristicSection[:s_exit] - - ##TODO: use a tuple with naming - pointsOfInterest = Tuple[] + CS_poi = NamedTuple[] if !isempty(MS_poi) for POI in MS_poi - s_poi = POI[1] + s_poi = POI[:s] if s_entry < s_poi && s_poi <= s_exit - push!(pointsOfInterest, (POI)) + push!(CS_poi, POI) end end end - if isempty(pointsOfInterest) || pointsOfInterest[end][1] < s_exit - push!(pointsOfInterest, (s_exit,"")) # s_exit has to be the last POI so that there will always be a POI to campare the current position with + if isempty(CS_poi) || CS_poi[end][:s] < s_exit + push!(CS_poi, (s = s_exit, label = "")) # s_exit has to be the last POI so that there will always be a POI to campare the current position with end - merge!(characteristicSection, Dict(:pointsOfInterest => pointsOfInterest)) + merge!(characteristicSection, Dict(:pointsOfInterest => CS_poi)) return characteristicSection end #function CharacteristicSection diff --git a/src/output.jl b/src/output.jl index a77688a..1737692 100644 --- a/src/output.jl +++ b/src/output.jl @@ -4,7 +4,7 @@ # __copyright__ = "2020-2022" # __license__ = "ISC" -function createOutput(settings::Settings, drivingCourse::Vector{Dict}, pointsOfInterest::Vector{Tuple}) +function createOutput(settings::Settings, drivingCourse::Vector{Dict}, pointsOfInterest::Vector{NamedTuple}) if settings.outputDetail == :running_time output::Vector{Dict} = [Dict(:t => drivingCourse[end][:t])] From bc02e96a6c1818977096cb40fe932c56d547d0d0 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Mon, 22 Aug 2022 19:07:49 +0200 Subject: [PATCH 11/14] Access elements from 'points of interests' by name instead of by index --- src/behavior.jl | 128 ++++++++++++++++++++++++------------------------ src/calc.jl | 2 +- src/output.jl | 2 +- 3 files changed, 65 insertions(+), 67 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index 10d3c88..2f111a7 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -105,7 +105,7 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, while !speedLimitReached && !endOfCSReached && tractionSurplus && !brakingStartReached && !previousSpeedLimitReached currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached @@ -129,7 +129,7 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] speedLimitReached = drivingCourse[end][:v] >= CS[:v_limit] previousSpeedLimitReached = lowestSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > lowestSpeedLimit[:v] || (drivingCourse[end][:v] == lowestSpeedLimit[:v] && drivingCourse[end][:s] < lowestSpeedLimit[:s_end])) - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] # POIs include s_exit as well + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] # POIs include s_exit as well tractionSurplus = drivingCourse[end][:F_T] > drivingCourse[end][:F_R] end #while @@ -149,10 +149,10 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, testFlag && println("in CS",csId," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing currentStepSize = settings.stepSize / 10.0^cycle - elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[1]) # for testing + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[:s]) # for testing if settings.stepVariable == :distance - currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] + currentStepSize = nextPointOfInterest[:s] - drivingCourse[end-1][:s] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -176,16 +176,16 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, testFlag && println("in CS",csId," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing break - elseif drivingCourse[end][:s] == nextPointOfInterest[1] - testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[1]) # for testing - if nextPointOfInterest[1] == CS[:s_exit] + elseif drivingCourse[end][:s] == nextPointOfInterest[:s] + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[:s]) # for testing + if nextPointOfInterest[:s] == CS[:s_exit] endOfCSReached = true end break else println("v=",drivingCourse[end][:v]," v_limit= ", CS[:v_limit] , " v_lowestLimit=", lowestSpeedLimit[:v]) - println("s=" ,drivingCourse[end][:s]," s_exit=", CS[:s_exit], " s+s_braking=", drivingCourse[end][:s] +s_braking," nextPOI=",nextPointOfInterest[1]) + println("s=" ,drivingCourse[end][:s]," s_exit=", CS[:s_exit], " s+s_braking=", drivingCourse[end][:s] +s_braking," nextPOI=",nextPointOfInterest[:s]) println("F_T=",drivingCourse[end][:F_T] ," F_R=", drivingCourse[end][:F_R]) error("ERROR at accelerating section: With the step variable ",settings.stepVariable," the while loop will be left although v nextPointOfInterest[1] - testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing - drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing + drivingCourse[end][:s] = nextPointOfInterest[:s] # round s down to nextPointOfInterest elseif drivingCourse[end][:F_T] <= drivingCourse[end][:F_R] testFlag && println("in CS",csId," accelerating cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," <= F_R=",drivingCourse[end][:F_R]) # for testing @@ -245,8 +245,8 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, if drivingCourse[end][:s] == CS[:s_exit] endOfCSReached = true end - if drivingCourse[end][:s] == nextPointOfInterest[1] - drivingCourse[end][:label] = nextPointOfInterest[2] + if drivingCourse[end][:s] == nextPointOfInterest[:s] + drivingCourse[end][:label] = nextPointOfInterest[:label] end end #while @@ -315,7 +315,7 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: while trainInPreviousCS && !targetPositionReached && !tractionDeficit && (trainIsClearing || (trainIsBrakingDownhill == resistingForceNegative)) # while clearing tractive or braking force can be used currentStepSize = settings.stepSize nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while trainInPreviousCS && !targetPositionReached && !pointOfInterestReached && !tractionDeficit && (trainIsClearing || (trainIsBrakingDownhill == resistingForceNegative)) # while clearing tractive or braking force can be used @@ -344,7 +344,7 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: calculateForces!(drivingCourse[end], CSs, csId, "default", train, settings.massModel) # conditions for the next while cycle - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] # POIs include s_exit as well + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] # POIs include s_exit as well tractionDeficit = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] targetPositionReached = drivingCourse[end][:s] >= targetPosition trainInPreviousCS = drivingCourse[end][:s] < CS[:s_entry] + train.length @@ -362,9 +362,9 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: elseif trainIsBrakingDownhill && !resistingForceNegative currentStepSize = settings.stepSize / 10.0^cycle - elseif drivingCourse[end][:s] > nextPointOfInterest[1] + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] if settings.stepVariable == :distance - currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] + currentStepSize = nextPointOfInterest[:s] - drivingCourse[end-1][:s] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -382,7 +382,7 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: elseif drivingCourse[end][:s] >= CS[:s_entry] + train.length break - elseif drivingCourse[end][:s] == nextPointOfInterest[1] + elseif drivingCourse[end][:s] == nextPointOfInterest[:s] break elseif !trainInPreviousCS @@ -403,8 +403,8 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: resistingForceNegative = drivingCourse[end][:F_R] < 0.0 else # if the level of approximation is reached - if drivingCourse[end][:s] > nextPointOfInterest[1] - drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest + if drivingCourse[end][:s] > nextPointOfInterest[:s] + drivingCourse[end][:s] = nextPointOfInterest[:s] # round s down to nextPointOfInterest elseif drivingCourse[end][:s] > targetPosition if drivingMode != "clearing" pop!(drivingCourse) @@ -426,8 +426,8 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: end end #for - if drivingCourse[end][:s] == nextPointOfInterest[1] - drivingCourse[end][:label] = nextPointOfInterest[2] + if drivingCourse[end][:s] == nextPointOfInterest[:s] + drivingCourse[end][:label] = nextPointOfInterest[:label] end end #while @@ -440,8 +440,8 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: while !targetPositionReached && !tractionDeficit && (trainIsClearing || (trainIsBrakingDownhill == resistingForceNegative)) # while clearing tractive or braking force can be used nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) - if nextPointOfInterest[1] > targetPosition - nextPointOfInterest = [targetPosition, ""] + if nextPointOfInterest[:s] > targetPosition + nextPointOfInterest = (s = targetPosition, label = "") #[targetPosition, ""] end # tractive effort (in N): @@ -457,13 +457,13 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: # calculate the remaining cruising way #s_cruisingRemaining=targetPosition-drivingCourse[end][:s] - s_cruisingRemaining = min(nextPointOfInterest[1] -drivingCourse[end][:s], targetPosition -drivingCourse[end][:s]) + s_cruisingRemaining = min(nextPointOfInterest[:s] -drivingCourse[end][:s], targetPosition -drivingCourse[end][:s]) # create the next support point push!(drivingCourse, moveAStep(drivingCourse[end], :distance, s_cruisingRemaining, csId)) drivingCourse[end][:behavior] = drivingMode - if drivingCourse[end][:s] == nextPointOfInterest[1] - drivingCourse[end][:label] = nextPointOfInterest[2] + if drivingCourse[end][:s] == nextPointOfInterest[:s] + drivingCourse[end][:label] = nextPointOfInterest[:label] end calculateForces!(drivingCourse[end], CSs, csId, "default", train, settings.massModel) @@ -514,11 +514,10 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C while tractionDeficit && !targetSpeedReached && !endOfCSReached && !brakingStartReached currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while tractionDeficit && !brakingStartReached && !pointOfInterestReached && !targetSpeedReached - # 03/09 old: while drivingCourse[end][:F_T] < drivingCourse[end][:F_R] && !brakingStartReached && drivingCourse[end][:s] < nextPointOfInterest[1] && drivingCourse[end][:v]>0.0 # as long as s_i + s_braking < s_end # acceleration (in m/s^2): drivingCourse[end][:a] = acceleration(drivingCourse[end][:F_T], drivingCourse[end][:F_R], train.m_train_full, train.ξ_train) @@ -532,7 +531,7 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit] - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] targetSpeedReached = drivingCourse[end][:v] <= 0.0 tractionDeficit = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] endOfCSReached = drivingCourse[end][:s] == CS[:s_exit] @@ -560,10 +559,10 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C testFlag && println("in CS",csId," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing currentStepSize = settings.stepSize / 10.0^cycle - elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[1]) # for testing + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPOI=",nextPointOfInterest[:s]) # for testing if settings.stepVariable == :distance - currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] + currentStepSize = nextPointOfInterest[:s] - drivingCourse[end-1][:s] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -572,8 +571,8 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C testFlag && println("in CS",csId," diminishing cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing break - elseif drivingCourse[end][:s] == nextPointOfInterest[1] - testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[1]) # for testing + elseif drivingCourse[end][:s] == nextPointOfInterest[:s] + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[:s]) # for testing break elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] @@ -614,9 +613,9 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C tractionDeficit = true endOfCSReached = false - elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing - drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing + drivingCourse[end][:s] = nextPointOfInterest[:s] # round s down to nextPointOfInterest elseif drivingCourse[end][:F_T] >= drivingCourse[end][:F_R] testFlag && println("in CS",csId," diminishing cycle",cycle," case: F_T=", drivingCourse[end][:F_T]," >= F_R=", drivingCourse[end][:F_R]) # for testing @@ -625,7 +624,7 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C else testFlag && println("in CS",csId," diminishing cycle",cycle," case: else with v=", drivingCourse[end][:v]," > 0.0 and F_T=", drivingCourse[end][:F_T]," <= F_R=", drivingCourse[end][:F_R]) # for testing #println(" and s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," <= s_exit=",CS[:s_exit]) # for testing - #println(" and s=", drivingCourse[end][:s]," <= nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + #println(" and s=", drivingCourse[end][:s]," <= nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing # if drivingCourse[end][:s] + s_braking == CS[:s_exit] # brakingStartReached = true @@ -639,8 +638,8 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C end #if end #for - if drivingCourse[end][:s] == nextPointOfInterest[1] - drivingCourse[end][:label] = nextPointOfInterest[2] + if drivingCourse[end][:s] == nextPointOfInterest[:s] + drivingCourse[end][:label] = nextPointOfInterest[:label] end end #while end @@ -679,8 +678,8 @@ function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: while !targetSpeedReached && !endOfCSReached && !brakingStartReached currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections - nextPointOfInterest[1] = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + nextPointOfInterest[:s] = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while !targetSpeedReached && !brakingStartReached && !pointOfInterestReached @@ -702,7 +701,7 @@ function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: # conditions for the next while cycle s_braking = brakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel) brakingStartReached = drivingCourse[end][:s] + s_braking >= CS[:s_exit] - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] || drivingCourse[end][:v] > CS[:v_limit] || lowestSpeedLimit[:v] < CS[:v_limit] && (drivingCourse[end][:v] > lowestSpeedLimit[:v] || (drivingCourse[end][:v] == lowestSpeedLimit[:v] && drivingCourse[end][:s] < lowestSpeedLimit[:s_end])) end # while @@ -714,10 +713,10 @@ function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: testFlag && println("in CS",csId," coasting cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing currentStepSize = settings.stepSize / 10.0^cycle - elseif drivingCourse[end][:s] > nextPointOfInterest[1] - testFlag && println("in CS",csId," coasting cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + testFlag && println("in CS",csId," coasting cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing if settings.stepVariable == :distance - currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] + currentStepSize = nextPointOfInterest[:s] - drivingCourse[end-1][:s] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -746,8 +745,8 @@ function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: testFlag && println("in CS",csId," coasting cycle",cycle," case: v=", drivingCourse[end][:v]," == v_exit=", CS[:v_exit]) # for testing break - elseif drivingCourse[end][:s] == nextPointOfInterest[1] - testFlag && println("in CS",csId," coasting cycle",cycle," case: s =", drivingCourse[end][:s]," > nextPointOfInterest[1]=",nextPointOfInterest[1]) # for testing + elseif drivingCourse[end][:s] == nextPointOfInterest[:s] + testFlag && println("in CS",csId," coasting cycle",cycle," case: s =", drivingCourse[end][:s]," > nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing break else @@ -791,16 +790,16 @@ function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: speedLimitReached = true end - elseif drivingCourse[end][:s] > nextPointOfInterest[1] - drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + drivingCourse[end][:s] = nextPointOfInterest[:s] # round s down to nextPointOfInterest else # do nothing for example for drivingCourse[end][:s] + s_braking == CS[:s_exit] end end end #for - if drivingCourse[end][:s] == nextPointOfInterest[1] - drivingCourse[end][:label] = nextPointOfInterest[2] + if drivingCourse[end][:s] == nextPointOfInterest[:s] + drivingCourse[end][:label] = nextPointOfInterest[:label] end end #while @@ -836,11 +835,10 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: while !targetSpeedReached && !endOfCSReached currentStepSize = settings.stepSize # initialize the step size that can be reduced near intersections nextPointOfInterest = getNextPointOfInterest(CS[:pointsOfInterest], drivingCourse[end][:s]) - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] for cycle in 1:settings.approxLevel+1 # first cycle with normal step size followed by cycles with reduced step size depending on the level of approximation while !targetSpeedReached && !endOfCSReached && !pointOfInterestReached - # 03/09 old: while drivingCourse[end][:v] > CS[:v_exit] && !targetSpeedReached && drivingCourse[end][:s] < CS[:s_exit] && drivingCourse[end][:s] < nextPointOfInterest[1] # traction effort and resisting forces (in N): calculateForces!(drivingCourse[end], CSs, csId, drivingMode, train, settings.massModel) @@ -860,7 +858,7 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: end # conditions for the next while cycle - pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1] + pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit] end # while @@ -875,9 +873,9 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: currentStepSize = settings.stepSize / 10.0^cycle end - elseif drivingCourse[end][:s] > nextPointOfInterest[1] + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] if settings.stepVariable == :distance - currentStepSize = nextPointOfInterest[1] - drivingCourse[end-1][:s] + currentStepSize = nextPointOfInterest[:s] - drivingCourse[end-1][:s] else currentStepSize = settings.stepSize / 10.0^cycle end @@ -895,7 +893,7 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: targetSpeedReached = true break - elseif drivingCourse[end][:s] == nextPointOfInterest[1] + elseif drivingCourse[end][:s] == nextPointOfInterest[:s] break end @@ -920,8 +918,8 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: # recalculateLastBrakingPoint!(drivingCourse, CS[:s_exit], CS[:v_exit]) drivingCourse[end][:s] = CS[:s_exit] break - elseif drivingCourse[end][:s] > nextPointOfInterest[1] - drivingCourse[end][:s] = nextPointOfInterest[1] # round s down to nextPointOfInterest + elseif drivingCourse[end][:s] > nextPointOfInterest[:s] + drivingCourse[end][:s] = nextPointOfInterest[:s] # round s down to nextPointOfInterest break elseif drivingCourse[end][:v] == CS[:v_exit] && drivingCourse[end][:s] == CS[:s_exit] break @@ -942,13 +940,13 @@ function addBrakingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs:: targetSpeedReached = true break else - # do nothing for example for drivingCourse[end][:s]==nextPointOfInterest[1] + # do nothing for example for drivingCourse[end][:s]==nextPointOfInterest[:s] end end end #for - if drivingCourse[end][:s] == nextPointOfInterest[1] - drivingCourse[end][:label] = nextPointOfInterest[2] + if drivingCourse[end][:s] == nextPointOfInterest[:s] + drivingCourse[end][:label] = nextPointOfInterest[:label] end end #while diff --git a/src/calc.jl b/src/calc.jl index 6f5f293..b07ae21 100644 --- a/src/calc.jl +++ b/src/calc.jl @@ -299,7 +299,7 @@ TODO """ function getNextPointOfInterest(pointsOfInterest::Vector{NamedTuple}, s::Real) for POI in pointsOfInterest - if POI[1] > s + if POI[:s] > s return POI end end diff --git a/src/output.jl b/src/output.jl index 1737692..e77e350 100644 --- a/src/output.jl +++ b/src/output.jl @@ -19,7 +19,7 @@ function createOutput(settings::Settings, drivingCourse::Vector{Dict}, pointsOfI supportPoint = 1 for POI in 1:length(pointsOfInterest) while supportPoint <= length(drivingCourse) - if pointsOfInterest[POI][1] == drivingCourse[supportPoint][:s] + if pointsOfInterest[POI][:s] == drivingCourse[supportPoint][:s] push!(output, drivingCourse[supportPoint]) break end From a7fe8db1c2ce6cc44acc44d62591c9fedcbfd2a4 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 24 Aug 2022 10:07:30 +0200 Subject: [PATCH 12/14] Refactor setting the state flag :endOfCsReached --- src/behavior.jl | 28 +++------------------------- 1 file changed, 3 insertions(+), 25 deletions(-) diff --git a/src/behavior.jl b/src/behavior.jl index 2f111a7..76795ac 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -167,9 +167,6 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, elseif drivingCourse[end][:s] + s_braking == CS[:s_exit] testFlag && println("in CS",csId," accelerating cycle",cycle," case: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," == s_exit=",CS[:s_exit]) # for testing - if s_braking == 0.0 - endOfCSReached = true - end break elseif drivingCourse[end][:v] == lowestSpeedLimit[:v] @@ -178,9 +175,6 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, elseif drivingCourse[end][:s] == nextPointOfInterest[:s] testFlag && println("in CS",csId," accelerating cycle",cycle," case: s=", drivingCourse[end][:s]," == nextPOI=",nextPointOfInterest[:s]) # for testing - if nextPointOfInterest[:s] == CS[:s_exit] - endOfCSReached = true - end break else @@ -197,7 +191,6 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, brakingStartReached = false previousSpeedLimitReached = false speedLimitReached = false - endOfCSReached = false pointOfInterestReached = false tractionSurplus = true @@ -228,17 +221,12 @@ function addAcceleratingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, else if drivingCourse[end][:s] + s_braking == CS[:s_exit] testFlag && println("in CS",csId," accelerating cycle",cycle," else case and there: s +s_braking=", drivingCourse[end][:s],",+",s_braking," = ",drivingCourse[end][:s] +s_braking," > s_exit=",CS[:s_exit]) # for testing + elseif drivingCourse[end][:v] == lowestSpeedLimit[:v] testFlag && println("in CS",csId," accelerating cycle",cycle," case: v=", drivingCourse[end][:v]," == v_lowestLimit=", lowestSpeedLimit[:v]) # for testing end end - - # TODO is it possible to put this into to the if-fork? - if drivingCourse[end][:s] == CS[:s_exit] - endOfCSReached = true - end - end end #for @@ -534,7 +522,6 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[:s] targetSpeedReached = drivingCourse[end][:v] <= 0.0 tractionDeficit = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] - endOfCSReached = drivingCourse[end][:s] == CS[:s_exit] end #while if csId==0 @@ -595,7 +582,6 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C pointOfInterestReached = false targetSpeedReached = false tractionDeficit = true - endOfCSReached = false else # if the level of approximation is reached if drivingCourse[end][:v] <= 0.0 @@ -611,7 +597,6 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C pointOfInterestReached = false targetSpeedReached = false tractionDeficit = true - endOfCSReached = false elseif drivingCourse[end][:s] > nextPointOfInterest[:s] testFlag && println("in CS",csId," diminishing cycle",cycle," case: s=", drivingCourse[end][:s]," > nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing @@ -625,19 +610,11 @@ function addDiminishingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, C testFlag && println("in CS",csId," diminishing cycle",cycle," case: else with v=", drivingCourse[end][:v]," > 0.0 and F_T=", drivingCourse[end][:F_T]," <= F_R=", drivingCourse[end][:F_R]) # for testing #println(" and s +s_braking=", drivingCourse[end][:s],"+",s_braking," = ",drivingCourse[end][:s] +s_braking," <= s_exit=",CS[:s_exit]) # for testing #println(" and s=", drivingCourse[end][:s]," <= nextPointOfInterest[:s]=",nextPointOfInterest[:s]) # for testing - - # if drivingCourse[end][:s] + s_braking == CS[:s_exit] - # brakingStartReached = true - # end end #if - - # # TODO is it possible to put this into to the if-fork? - # if drivingCourse[end][:s] == CS[:s_exit] - # endOfCSReached = true - # end end #if end #for + endOfCSReached = drivingCourse[end][:s] == CS[:s_exit] if drivingCourse[end][:s] == nextPointOfInterest[:s] drivingCourse[end][:label] = nextPointOfInterest[:label] end @@ -798,6 +775,7 @@ function addCoastingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: end end #for + endOfCSReached = drivingCourse[end][:s] == CS[:s_exit] if drivingCourse[end][:s] == nextPointOfInterest[:s] drivingCourse[end][:label] = nextPointOfInterest[:label] end From 804f797b08f221ce9a996716b64ad281b5e25981 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Wed, 24 Aug 2022 10:08:20 +0200 Subject: [PATCH 13/14] Fix typing error (change time to :time) --- src/behavior.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/behavior.jl b/src/behavior.jl index 76795ac..34d11e6 100644 --- a/src/behavior.jl +++ b/src/behavior.jl @@ -321,7 +321,7 @@ function addCruisingSection!(drivingCourse::Vector{Dict}, stateFlags::Dict, CSs: drivingCourse[end][:a] = 0.0 # create the next support point - if settings.stepVariable == :distance || settings.stepVariable == time + if settings.stepVariable == :distance || settings.stepVariable == :time push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, currentStepSize, csId)) else push!(drivingCourse, moveAStep(drivingCourse[end], settings.stepVariable, train.length/(10.0^cycle), csId)) # TODO which step size should be used? From 8b3d16517be98f22062b012452a9483fbfd3ce33 Mon Sep 17 00:00:00 2001 From: Max Kannenberg <95709892+MaxKannenberg@users.noreply.github.com> Date: Mon, 29 Aug 2022 12:52:25 +0200 Subject: [PATCH 14/14] Update changelog --- CHANGELOG.md | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dbe662d..c25f502 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,6 +9,22 @@ Categories: Added, Changed, Deprecated, Removed, Fixed, and Security. ## [Unreleased] +### Added +* output alternative with starting points of the driving modes + +### Changed +* renamed data points into 'support points' +* reduced number of decimal places of output data +* replace v_peak by the existing v_limit +* changed type of a point of interest from Tuple to NamedTuple + +### Removed +* dictionary MovingSection +* redundant keys from the dictionary CharacteristicSection +* dictionary BehaviorSection +* redundant keys from the dictionary SupportPoint +* function secureAcceleratingBehavior() + ## Version [1.0.1] 2022-06-05 @@ -208,4 +224,4 @@ Proof of concept and master thesis submission. [0.4]: https://github.com/railtoolkit/TrainRuns.jl/compare/v0.3...v0.4 [0.3]: https://github.com/railtoolkit/TrainRuns.jl/compare/v0.2...v0.3 [0.2]: https://github.com/railtoolkit/TrainRuns.jl/compare/v0.1...v0.2 -[0.1]: https://github.com/railtoolkit/TrainRuns.jl/releases/tag/v0.1 \ No newline at end of file +[0.1]: https://github.com/railtoolkit/TrainRuns.jl/releases/tag/v0.1