The original design of my CFS program used the notion of a Shipment, which implemented the basic idea of a shipper sending a load of something to a receiver, much as one would expect. The starting and ending tracks could be either in the modelled network (on the layout) or at virtual tracks in the unmodelled space (behind staging). With this approach, only the loaded segment of a car’s journey is defined, regardless of if it is heading in to or out from the modelled layout. Every car’s assignment will always include at least one segment that is done empty, either to supply a car to a shipper to be loaded, or to return an unloaded empty car back home, or both. With a Shipment having only information for the loaded segment, the other segment(s) must be generated using some sort of rules. The various rules tried so far have been less than entirely satisfactory, and this has led to some unfortunate side effects in terms of not being able to shape car movements in desirable ways.
A good example of this problem is when a car is supplied to a modelled shipper. The car will usually come from one of the staging tracks, but which one? The shipment is silent about where a car comes from, or where it returns to. When restaging a car, we may not want the selection process to consider all staging tracks equally, as that may have ramifications on car interchanges, flow through yards, etc. It would be better if there was a way to influence this selection process by having relative weights on the different choices, so that some are more likely to be selected than others. This allows for some oddball routing for variety, but the bulk of the selections will be what we expect.
Similarly, the choice of which way to route an empty car towards home suffers from the same problem. While there are lots of prototype rules around this, the reality on a model railroad is that we may have to coerce the routing so that parts of the layout do not get overloaded. Again, having a weighting scheme would help.
A simple solution to both problems is to define a complete life cycle for each shipment, including car supply, freight movement, and empty return. Each role is given a weighting that can be used when selecting from otherwise equal and suitable choices. For example, car routings that do not involve interchange to other railroads may be given a higher weighting and therefore are more likely to be selected than ones that have interchange, thereby minimizing cars having to be switched through a yard.
This new notion is called a “Role” for now, so that it can coexist with the current Shipments, but the name may get changed back to just “Shipment” after the original Shipment concept has been completely removed from the code.
One major benefit of this approach is that car life cycles that are more complicated than just a simple supply, freight, and return sequence become very easy to implement, as the role will simply have more segments to be followed. Think of a reefer needing to be iced before it is loaded. It really needs to make two stops for “loading”, one for ice, and the other for the actual load. This new simpler scheme eliminates the need for convoluted rules to handle the extra car movements. It now becomes very easy to include some unusual shipments that should get selected only very infrequently, simply by giving them low weights.
In order to implement this change in the program, significant code must be changed, which will be a big job as the results must be checked carefully to make sure that it really is working as expected. Results from early testing look very promising.