Add the approxLevel from settings to formulary

development
Max Kannenberg 2022-05-19 21:45:10 +02:00
parent 250687a851
commit ae5cc07862
5 changed files with 26 additions and 26 deletions

View File

@ -246,7 +246,7 @@ function addBreakFreeSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags:
if haskey(stateFlags, :usedForDefiningCharacteristics) && stateFlags[:usedForDefiningCharacteristics]
s_braking = 0.0
else
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
# reset state flags
@ -272,7 +272,7 @@ function addClearingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::
s_braking = 0.0
else
ignoreBraking = false
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(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])
@ -310,7 +310,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla
s_braking = 0.0
else
ignoreBraking = false
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
# conditions for the accelerating section
@ -337,7 +337,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla
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 = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
while !targetSpeedReached && !speedLimitReached && !brakingStartReached && !pointOfInterestReached && tractionSurplus && !previousSpeedLimitReached
@ -359,7 +359,7 @@ function addAcceleratingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFla
# conditions for the next while cycle
if !ignoreBraking
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(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]
@ -558,11 +558,11 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::
s_braking = 0.0
else
ignoreBraking = false
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
# conditions for cruising section
#s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
#s_braking = calcBrakingDistance(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]
tractionDeficit = drivingCourse[end][:F_T] < drivingCourse[end][:F_R]
@ -785,7 +785,7 @@ function addCruisingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::
# set state flags
stateFlags[:endOfCSReached] = drivingCourse[end][:s] == CS[:s_exit]
if !ignoreBraking
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
stateFlags[:brakingStartReached] = brakingStartReached || drivingCourse[end][:s] + s_braking >= CS[:s_exit]
stateFlags[:tractionDeficit] = tractionDeficit
@ -807,14 +807,14 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag
s_braking = 0.0
else
ignoreBraking = false
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
# conditions for diminishing section
targetSpeedReached = drivingCourse[end][:v] <= 0.0
endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached]
tractionDeficit = drivingCourse[end][:F_T] < drivingCourse[end][:F_R] #|| stateFlags[:tractionDeficit]
#s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
#s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
brakingStartReached = drivingCourse[end][:s] + s_braking >= CS[:s_exit] || stateFlags[:brakingStartReached]
# use the conditions for the diminishing section
@ -842,7 +842,7 @@ function addDiminishingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlag
# conditions for the next while cycle
if !ignoreBraking
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
end
brakingStartReached = drivingCourse[end][:s] +s_braking >= CS[:s_exit]
pointOfInterestReached = drivingCourse[end][:s] >= nextPointOfInterest[1]
@ -994,7 +994,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::
targetSpeedReached = drivingCourse[end][:v] <= CS[:v_exit]
endOfCSReached = drivingCourse[end][:s] >= CS[:s_exit] || stateFlags[:endOfCSReached]
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking, settings.approxLevel)
brakingStartReached = drivingCourse[end][:s] + s_braking >= CS[:s_exit] || stateFlags[:brakingStartReached]
# use the conditions for the coasting section
@ -1022,7 +1022,7 @@ function addCoastingSection!(CS::Dict, drivingCourse::Vector{Dict}, stateFlags::
push!(BS[:dataPoints], drivingCourse[end][:i])
# conditions for the next while cycle
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(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]

View File

@ -32,7 +32,7 @@ function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, t
end
# determine the different flags for switching between the states for creatinge moving phases
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(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)
previousSpeedLimitReached = false
@ -69,7 +69,7 @@ function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, t
(CS, drivingCourse, stateFlags) = addCruisingSection!(CS, drivingCourse, stateFlags, s_cruising, settings, train, CSs, "cruising")
elseif drivingCourse[end][:F_R] < 0 && stateFlags[:speedLimitReached]
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(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
@ -79,7 +79,7 @@ function calculateMinimumRunningTime!(movingSection::Dict, settings::Settings, t
end
elseif drivingCourse[end][:F_T] == drivingCourse[end][:F_R] || stateFlags[:speedLimitReached]
s_braking = calcBrakingDistance(drivingCourse[end][:v], CS[:v_exit], train.a_braking)
s_braking = calcBrakingDistance(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 # TODO: define a minimum cruising length?

View File

@ -8,7 +8,7 @@
## create a moving section and its containing characteristic sections with secured braking, accelerating and cruising behavior
function determineCharacteristics(path::Path, train::Train, settings::Settings)
movingSection = createMovingSection(path, train.v_limit, train.length)
movingSection = secureBrakingBehavior!(movingSection, train.a_braking)
movingSection = secureBrakingBehavior!(movingSection, train.a_braking, settings.approxLevel)
movingSection = secureAcceleratingBehavior!(movingSection, settings, train)
#movingSection = secureCruisingBehavior!(movingSection, settings, train)
@ -16,7 +16,7 @@ function determineCharacteristics(path::Path, train::Train, settings::Settings)
end #function determineCharacteristics
## define the intersection velocities between the characterisitc sections to secure braking behavior
function secureBrakingBehavior!(movingSection::Dict, a_braking::Real)
function secureBrakingBehavior!(movingSection::Dict, a_braking::Real, approxLevel::Integer)
# this function limits the entry and exit velocity of the characteristic sections to secure that the train stops at the moving sections end
CSs = movingSection[:characteristicSections]
@ -27,7 +27,7 @@ function secureBrakingBehavior!(movingSection::Dict, a_braking::Real)
CS[:v_exit] = min(CS[:v_limit], followingCSv_entry)
v_entryMax = calcBrakingStartVelocity(CS[:v_exit], a_braking, CS[:length])
v_entryMax = calcBrakingStartVelocity(CS[:v_exit], a_braking, CS[:length], approxLevel)
CS[:v_entry] = min(CS[:v_limit], v_entryMax)
CS[:v_peak] = CS[:v_entry]

View File

@ -28,7 +28,7 @@
## }
#########################
approxLevel = 6
#approxLevel = 6
v00 = 100/3.6 # velocity factor (in m/s)
## calculate forces
@ -206,7 +206,7 @@ function calc_ΔE(ΔW::Real)
return ΔE
end #function calc_ΔW
function calcBrakingDistance(v_start::Real, v_end::Real, a_braking::Real)
function calcBrakingDistance(v_start::Real, v_end::Real, a_braking::Real, approxLevel::Integer)
# equation is based on [Wende:2003, page 37]
# v_start: velocity at the start of braking (in m/s)
@ -215,18 +215,18 @@ function calcBrakingDistance(v_start::Real, v_end::Real, a_braking::Real)
s_braking = (v_end^2 - v_start^2) /2 /a_braking # braking distance (in m)
# TODO: also possible: calc_Δs_with_Δv(v_end-v_start, a_braking, v_start)
# return max(0.0, ceil(s_braking, digits=approxLevel)) # ceil is used to be sure that the train stops at s_exit in spite of rounding errors
return max(0.0, ceil(s_braking, digits=approxLevel +1)) # ceil is used to be sure that the train stops at s_exit in spite of rounding errors
return max(0.0, ceil(s_braking, digits= approxLevel +1)) # ceil is used to be sure that the train stops at s_exit in spite of rounding errors
end #function calcBrakingDistance
function calcBrakingStartVelocity(v_end::Real, a_braking::Real, s_braking::Real)
function calcBrakingStartVelocity(v_end::Real, a_braking::Real, s_braking::Real, approxLevel::Integer)
# equation is based on [Wende:2003, page 37]
# v_end: target velocity at the end of braking (in m/s)
# a_braking: constant braking acceleration (in m/s^2)
# s_braking: braking distance (in Ws)
v_start = sqrt(v_end^2 - 2*a_braking *s_braking) # braking start velocity (in m/s)
# return floor(v_start, digits=approxLevel)
return floor(v_start, digits=approxLevel +1)
# return floor(v_start, digits= approxLevel)
return floor(v_start, digits= approxLevel +1)
end #function calcBrakingStartVelocity
function calcBrakingAcceleration(v_start::Real, v_end::Real, s_braking::Real)

View File

@ -10,7 +10,7 @@ struct Settings
massModel::Symbol # model type of train mass ":mass_point" or ":homogeneous_strip".
stepVariable::Symbol # variable of the linear multistep method: ":distance", ":time" or ":velocity".
stepSize::Real # step size, unit depends on stepVariable - :distance in meter, time in seconds and velocity in meter/second.
approxLevel::Int # value for approximation; used when rounding or interating.
approxLevel::Int # value for approximation; used when rounding or iterating.
outputDetail::Symbol # single Float() ":running_time", Array() of ":points_of_interest",
# complete Array() ":driving_course", or Dict() ":everything".
outputFormat::Symbol # output as ":dataframe" or as ":dict".