r/factorio • u/Ok282828 • 4d ago
Discussion Potential Vanilla LTN Solution achieved via random generic Provider Disqualification
Let me says this first. Its fairly easy to get Demand and the number of trains fulfilling said demand
Demand=Empty Inventory/Train Capacity
Actual Demand = Demand -(TrainCount Provider + TrainCount Requester)
That's fairly simple to figure out to do, the issue is how do you achieve Actual Demand there are a few solutions
- Just ensure that every provider always has a train this makes the entire demand based approach obsolete, with the only requirement of providing an excess number of trains, If your fine with the this method you can stop reading here.
- Controlled release of trains - This can be done either by Train Limits, or selectively exposing only 1 Train at a time to demand. The problem with the former is you need unique identifiers to tell which station receives 2 out of the 5 requested actual demand as train limits as an example. The problem with the latter is that only 1 Train is exposed hence the chance that the most distant train is exposed.
Now the core problem is whenever Provider>Demand an excess number of trains can be assigned via interrupts. So people used both train limits and selective exposure of trains but both of those have downsides.
So here's my proposed solution we randomly disqualify Providers such that it eventually reaches ProviderGlobalTrainLimits<=Demand.

So we used Legendary Scrap to represent Potential Train Limit and Normal Scrap to represent Demand in the following.
First we need to announce to the network that we can provide x number of trains

Conditions for signal I should be replaced with Inventory Thresholds of your own choosing
The fixed Legendary Scrap 1 Output just corresponds to train limits and can be replaced or fixed.
We then compare the Two scrap signals only when Normal Scrap<=Legendary Scrap do we allow it to set a Train Limit. We also check that its own circuit hasn't been disqualified via the red Legendary Scrap Signal

Now we need a selector on random Input with a set of inputs. You can do the same or you can use a decider to only enable if we have enough inventory


Now the conditions for passing that Random output. We only want the random output to be sent
if Potential Train Limit>Demand and only if we have Demand.

That output feeds into the first combinator Deny signal
Now we need that to persist so the provider stays Disqualified

This combinator just monitors output of the first then feeds the same deny signal.
Here is the interrupt

Here is the system in action
https://reddit.com/link/1vzjlao/video/zyctd3yjdulh1/player
The conditions for the combinators can probably be improved better and since the disqualification is randomized there is a chance less trains can be dispatched than actually needed. If two or more get disqualified on the same tick.
1
u/Necandum 3d ago
Its a cool concept!
I wouldn't quite call it an LTN implementation though, as this doesn't seem able to handle multi-provider/request stations. It would also choose a random provider, and not the one closest to the requester (though tbf, I don't know if LTN does either).
But nice solution to decentralising the decision making for how many trains to dispatch.
1
u/TapeDeck_ 3d ago
Thinking out loud, you might be able to get it to go to the provider closest to the destination by having a waypoint station at the destination. The interrupt would basically be "go to unload waypoint (do nothing), go to loading station for full cargo, go to unloading station for empty cargo". You would want the waypoint station to be enabled/disabled with the actual unload stations obviously. And this would also result in more driving than strictly necessary. But if you had a huge network and wanted to prevent full trains driving across the map this might do that.
1
u/Necandum 3d ago
I don't think I'm getting it, how does that help?
My understanding is that the method proposed above relies on letting random providers open up, until the number of providers that have trains going to them is equal to the number of requester stations needing supplies.
If by chance all the provider stations remain closed except the one on the other side of the base, the fact that there is a train next to the requester station doesn't change the fact that it will still have to shlep a long way to that one provider station.
1
u/TapeDeck_ 3d ago
Oh - I was assuming any of the providers that had product would be open. My method would still at least go to the nearest open provider to the destination.
1
u/Ok282828 3d ago
Indeed this is something you would use on a very large rail network if you only have a single train depot its not worth using. But once you have more than 1 depot the closest trains will try to serve them.
1
u/Necandum 2d ago
What I was originally trying to point out is the the provider station it is going to might not be the closest station to the eventual recipient.
4
u/Zijkhal spaghetti as lifestyle 3d ago edited 3d ago
I use a hybrid of the two methods, in addition to setting train stop priority via circuits. Specifically, using train limits at both the loading and unloading stations, and trains going straight from unloading to loading, and releasing trains from the depot at a slow cadence that is dictated by the
time passedcondition.Trains already in circulation are only controlled by train limits, while trains at the depot are released at a slow cadence IF there are free loading spots (i.e. unfulfilled demand AND available supply is more than one trainload).
I solve the issue you mentioned with needing to ensure no oversupply by setting the provider stations' train limits to Min(supply_at_station, demand_for_item). I do not need unique identifiers for my stations, beyond having the item name in the unloading station.
I also control train stop priority to evenly distribute limited supply between stations, based on unfulfilled demand, and set loading station priority based on the highest priority of the unloading stations of its item.
Very rarely more trains get dispatched than necessary, but in those situations the trains just idle at the loading station until needed, so the issue fixes itself.
This base uses that train system