Page 1 of 1

[1.1.68] Bots enqueue for charging on overloaded roboports while empty ports are nearby

Posted: Thu Sep 15, 2022 12:05 am
by smcpeak
When there are a lot of logistic bots in a network, they tend to queue in large numbers on a small number of overloaded roboports even when there are unused roboports nearby.

Example screenshot:
bot-charging.jpg
bot-charging.jpg (1.14 MiB) Viewed 840 times
In this screenshot, the network has 2400 bots, with none free. It does not matter how many more bots are added, there will never be any free, because new bots just add themselves to the charging queue after their first trip. Throughput is limited by the charging capacity of a handful of roboports despite there being many available. (I am aware that this particular setup can be optimized by better placement of the iron and copper plates. I designed this little factory to easily and obviously reproduce the issue, but it happens even in factories with better placement when they are large enough.)

Also note that this is after researching robot speed 10, so travel time is short even to distant roboports, but here they refuse to go even a few tens of tiles away.

The problem seems to be with the algorithm used to prioritize which roboport to charge at. The page https://wiki.factorio.com/Logistic_network#Roboports describes the algorithm thusly:
If the queue on that roboport is too long, they eventually choose another port. This is specified by the ratio of <distance to different roboport in tiles> / <queue size of robots waiting>.
I believe this is referring to the queue size of the roboport the bot is waiting at, and the distance to an alternative candidate roboport. But let's consider some sample numbers. In my screenshot, I estimate there are around 40 bots waiting at the 10th roboport from the right, while the rightmost roboport is 40 tiles away and has no bots. Dividing these, we get 40/40. The quoted text does not say what the threshold is, but I surmise it is 1. Since 40/40 is not less than 1, those 40 bots continue to wait, while the 41st would switch. But that is absurd, since for bot #40, it would take less than a second to fly to the open port but (I estimate) around 10-20 seconds to wait in the queue.

By dividing distance by bots, the existing algorithm treats flying N tiles as equivalent to waiting for one bot in the queue (where N is the undocumented threshold, probably 1), but waiting is much more expensive than flying N tiles for any value of N consistent with observation. This also does not appear to take robot speed upgrades into account, nor the queue size of the candidate alternative.

I would suggest, when evaluating candidate roboports, that for each such roboport, we estimate charging time by calculating distance/speed + queue_size*charge_time, and select the roboport with the smallest estimated charge time. Ideally, this would be done when the bot first decides it needs to charge, rather than only after getting impatient waiting for its first choice, but this is still a sensible calculation even if only done after arriving at their first choice and deciding whether to switch.

Regardless of the cause, the current algorithm clearly produces bad results, as shown in the screenshot, and the game does not provide mitigation. The best solution seems to be to install mods that increase the charging capacity of individual roboports, but mods should not be required to overcome broken mechanics.

This issue has been reported a few times elsewhere, including:
The response in each case seems to some combination of "it's working as intended" and "any improvement would be too CPU intensive". I disagree with both. I think the example I've given (with attached save file) adequately falsifies the former, and I'm fairly confident this can be fixed (or greatly improved) by simply changing the arithmetic rather than doing any new computation.

Re: [1.1.68] Bots enqueue for charging on overloaded roboports while empty ports are nearby

Posted: Thu Sep 15, 2022 12:28 am
by Loewchen