Skip to content

Commit f921543

Browse files
committed
doc: stdcm: update the design docs (en)
1 parent 9ef4bc5 commit f921543

File tree

12 files changed

+478
-1105
lines changed

12 files changed

+478
-1105
lines changed

content/docs/reference/design-docs/stdcm/pathfinding_module/conflict_avoidance/index.en.md

+25-1
Original file line numberDiff line numberDiff line change
@@ -57,4 +57,28 @@ computing an
5757
[engineering allowance]({{< ref "docs/explanation/running_time_calculation/allowances" >}} "allowances")
5858
is a feature of the running-time
5959
calculation module. It adds a given delay between two points of
60-
a path, without affecting the speeds on the rest of the path.
60+
a path, without affecting the speeds on the rest of the path.
61+
62+
63+
## Post-processing
64+
65+
We **used to** compute the engineering allowances during the graph
66+
exploration, but that process was far too expensive. We used to
67+
run binary searches on full simulations, which would sometimes
68+
go back for a long distance in the path.
69+
70+
What we *actually need* is to know whether an engineering allowance
71+
is *possible* without causing any conflict. We can use heuristics
72+
here, as long as we're on the conservative side: we can't
73+
say that it's possible if it isn't, but missing solutions with
74+
extremely tight allowances isn't a bad thing in our use cases.
75+
76+
77+
But this change means that, once the solution is found, we can't
78+
simply concatenate the simulation results. We need to run
79+
a full simulation, with actual engineering allowances,
80+
that avoid any conflict. This step has been merged
81+
with the one described on the
82+
[standard allowance]({{< ref "docs/reference/design-docs/stdcm/pathfinding_module/standard_allowance" >}} "standard allowance")
83+
page, which is now run even when no standard allowance
84+
have been set.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
---
2+
title: "Conflict detection"
3+
linkTitle: "2 - Conflict detection"
4+
weight: 20
5+
---
6+
7+
8+
9+
Once we know what paths we can use, we need to know when they
10+
can actually be used.
11+
12+
The [documentation]({{< ref "docs/reference/design-docs/conflict-detection" >}} "documentation")
13+
of the conflict detection module explains how it's done internally.
14+
Generally speaking, a train is in conflict when it has to slow down
15+
because of a signal. In our case, that means the solution would not
16+
be valid, we need to arrive later (or earlier) to see the signal
17+
when it's not restricting anymore.
18+
19+
The complex part is that we need to do the conflict detection *incrementally*
20+
Which means that:
21+
1. When running simulations up to t=x, we need to know all conflicts
22+
that happen before x, *even if they're indirectly caused by a
23+
signal seen at t > x* down the path.
24+
2. We need to know the conflicts and resource uses right as they start
25+
even if their end time can't be defined yet.
26+
27+
28+
For that to be possible, we need to know where the train will go
29+
*after* the section that is being simulated (see
30+
[infra exploration]({{< ref "docs/reference/design-docs/stdcm/pathfinding_module/infrastructure_exploration" >}} "infra exploration"):
31+
we need some elements in the lookahead section).
32+
33+
To handle it, the conflict detection module
34+
returns an error when more lookahead is required. When it happens
35+
we extend it by cloning the infra explorer objets.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
---
2+
title: "Infrastructure exploration"
3+
linkTitle: "1 - Infrastructure exploration"
4+
weight: 10
5+
---
6+
7+
The first thing we need to define is *how we move through the infrastructure*,
8+
without dealing with conflicts yet.
9+
10+
We need a way to define and enumerate the different possible paths and
11+
explore the infrastructure graph, with several constraints:
12+
1. The path must be compatible with the given rolling stock
13+
(loading gauge / electrification / signaling system)
14+
2. At any point, we need to access path properties from its start up to the
15+
considered point. This includes block and route lists.
16+
3. We sometimes need to know where the train will go *after* the
17+
point being evaluated, for proper conflict detection
18+
19+
20+
21+
To do this, we have defined the class `InfraExplorer`. It uses blocks
22+
(sections from signal to signal) as a main subdivision.
23+
It has 3 sections: the current block, predecessors, and a "lookahead".
24+
25+
26+
![InfraExplorer structure](infra_explorer.svg)
27+
28+
29+
In this example, the green arrows are the predecessor blocks.
30+
What happens there is considered to be immutable.
31+
32+
The red arrow is the current block. This is where we run
33+
train and signaling simulations, and where we deal with conflicts.
34+
35+
The blue arrows are part of the lookahead. This section hasn't
36+
been simulated yet, its only purpose is to know in advance
37+
where the train will go next. In this example, it would tell us
38+
that the bottom right signal can be ignored entirely.
39+
**A different `InfraExplorer` would be instantiated that would
40+
go toward the bottom section instead of the top one**,
41+
but this would be the path currently being evaluated.
42+
43+
44+
The `InfraExplorer` is manipulated with two main functions
45+
(the accessors have been removed here for clarity):
46+
47+
```kotlin
48+
interface InfraExplorer {
49+
/**
50+
* Clone the current object and extend the lookahead by one route, for each route starting at
51+
* the current end of the lookahead section. The current instance is not modified.
52+
*/
53+
fun cloneAndExtendLookahead(): Collection<InfraExplorer>
54+
55+
/**
56+
* Move the current block by one, following the lookahead section. Can only be called when the
57+
* lookahead isn't empty.
58+
*/
59+
fun moveForward(): InfraExplorer
60+
}
61+
```
62+
63+
`cloneAndExtendLookahead()` is the method that actually enumerates the
64+
different paths, returning clones for each possibility.
65+
It's called when we need a more precise lookahead to properly identify
66+
conflicts, or when it's empty and we need to move forward.
67+
68+
A variation of this class can also keep track of the train simulation
69+
and time information (called `InfraExplorerWithEnvelope`).
70+
This is the version that is actually used to explore the infrastructure.

0 commit comments

Comments
 (0)