fix(forsyning): mindst fyldte kilde først kun blandt kilder med >= 25 % af et læs (ellers fyldeste) — foder-traktorer hentede 2-10k l i en gæringssilo der fyldes løbende; knappen viser Start for et flow der aldrig kom i gang, selv med vogn på (v1.57.0.0)
This commit is contained in:
@@ -193,7 +193,10 @@ end
|
||||
function ADFlowWagons.hasActivity(run, vehiclesById)
|
||||
for _, vehicleId in ipairs(run.vehicleIds or {}) do
|
||||
local vehicle = vehiclesById ~= nil and vehiclesById[vehicleId] or nil
|
||||
if vehicle ~= nil and (waiting[vehicle] ~= nil or fetching[vehicle] ~= nil or #ADHitch.rearImplementsOf(vehicle) > 0) then
|
||||
-- vogn bagpå tæller kun i et flow der er startet: et flow der aldrig kom i gang (fx 'ingen vogn', og spilleren
|
||||
-- har selv koblet på) skal vise Start, ikke Stop (in-game 29/9: Milk Store)
|
||||
local holdsWagon = vehicle ~= nil and ADRunsController.runningRuns[run.id] == true and #ADHitch.rearImplementsOf(vehicle) > 0
|
||||
if vehicle ~= nil and (waiting[vehicle] ~= nil or fetching[vehicle] ~= nil or holdsWagon) then
|
||||
return true
|
||||
end
|
||||
end
|
||||
|
||||
@@ -372,18 +372,26 @@ end
|
||||
-- Bedste kilde der har varen: mindst fyldte først for lagervarer, fyldeste først for
|
||||
-- varer hvis tanke løber fulde (ADSupplyPlanner). Siloer med varen i EGET lager går
|
||||
-- altid forud for dem der kun kan låne fra naboer. Returnerer et valg eller nil.
|
||||
local function findBestSource(markerStations, fillTypes, farmId)
|
||||
local getLoadCapacity -- defineret længere nede (læs-kapacitet til kildevalget)
|
||||
|
||||
local function findBestSource(markerStations, fillTypes, farmId, loadCapacity)
|
||||
local prefersFullest = ADSupplyPlanner.prefersFullestSource(getFillTypeNames(fillTypes))
|
||||
local ample = ADSupplyPlanner.ampleLevel(loadCapacity)
|
||||
local best = {[true] = {}, [false] = {}}
|
||||
for _, entry in ipairs(markerStations) do
|
||||
local level, isOwn = getStationFillLevel(entry.station, fillTypes, farmId)
|
||||
if level >= ADSmartPickup.MIN_USEFUL_LITERS and not isProtectedProductionInput(entry.station, fillTypes)
|
||||
and ADSupplyPlanner.isBetterSource(level, best[isOwn].level, prefersFullest) then
|
||||
and ADSupplyPlanner.isBetterSource(level, best[isOwn].level, prefersFullest, ample) then
|
||||
best[isOwn] = {level = level, marker = entry.marker, station = entry.station, isOwn = isOwn}
|
||||
end
|
||||
end
|
||||
|
||||
local choice = best[true].marker ~= nil and best[true] or best[false]
|
||||
-- eget lager går forud — men ikke en næsten tom egen tank frem for et rigeligt nabolager
|
||||
local own, other = best[true], best[false]
|
||||
local choice = own
|
||||
if own.marker == nil or (not prefersFullest and other.marker ~= nil and own.level < ample and other.level >= ample) then
|
||||
choice = other
|
||||
end
|
||||
if choice.marker == nil then
|
||||
return nil
|
||||
end
|
||||
@@ -412,7 +420,7 @@ function ADSmartPickup.findLeastFilledPickup(adEnv, driver)
|
||||
return nil
|
||||
end
|
||||
local groupMarkers = adEnv.ADGraphManager:getMapMarkersInGroup(firstMarker.group)
|
||||
return findBestSource(collectMarkerStations(adEnv, groupMarkers, farmId, nil), fillTypes, farmId)
|
||||
return findBestSource(collectMarkerStations(adEnv, groupMarkers, farmId, nil), fillTypes, farmId, getLoadCapacity(adEnv, driver))
|
||||
end
|
||||
|
||||
-- Lagrene bag aflæsningsstationen; produktionspunkter uden targetStorages læses direkte.
|
||||
@@ -719,7 +727,7 @@ function ADSmartPickup.getTargetNeedsRanked(station, fillTypes, farmId, pending)
|
||||
end
|
||||
|
||||
-- Vognens samlede kapacitet (liter); nil hvis AutoDrive ikke kan opgøre den.
|
||||
local function getLoadCapacity(adEnv, driver)
|
||||
getLoadCapacity = function(adEnv, driver)
|
||||
if adEnv.AutoDrive.getAllUnits == nil or adEnv.AutoDrive.getAllFillLevels == nil then
|
||||
return nil
|
||||
end
|
||||
@@ -787,7 +795,7 @@ function ADSmartPickup.findSupplyPickup(adEnv, driver, ingredients, targetWayPoi
|
||||
-- bedste foder først: lavere foder kun når truget er nødlidende (ADSupplyPlanner.isFoodAllowed)
|
||||
local bestFood = ADSupplyPlanner.bestFoodPriority ~= nil and ADSupplyPlanner.bestFoodPriority(ranked) or nil
|
||||
for _, need in ipairs(ranked) do
|
||||
local choice = (ADSupplyPlanner.isFoodAllowed == nil or ADSupplyPlanner.isFoodAllowed(need, bestFood)) and findBestSource(markerStations, {need.fillType}, farmId) or nil
|
||||
local choice = (ADSupplyPlanner.isFoodAllowed == nil or ADSupplyPlanner.isFoodAllowed(need, bestFood)) and findBestSource(markerStations, {need.fillType}, farmId, loadCapacity) or nil
|
||||
if choice ~= nil then
|
||||
return {
|
||||
markerIndex = choice.markerIndex,
|
||||
|
||||
@@ -29,15 +29,32 @@ function ADSupplyPlanner.prefersFullestSource(fillTypeNames)
|
||||
return true
|
||||
end
|
||||
|
||||
-- "Rigelig" kilde: kan levere mindst MIN_LOAD_SHARE af et læs (mindst MIN_AMPLE_LITERS).
|
||||
ADSupplyPlanner.MIN_LOAD_SHARE = 0.25
|
||||
ADSupplyPlanner.MIN_AMPLE_LITERS = 5000
|
||||
|
||||
function ADSupplyPlanner.ampleLevel(loadCapacity)
|
||||
return math.max(ADSupplyPlanner.MIN_AMPLE_LITERS, (loadCapacity or 0) * ADSupplyPlanner.MIN_LOAD_SHARE)
|
||||
end
|
||||
|
||||
-- Er en kilde med dette niveau bedre end den hidtil bedste (nil = ingen endnu)?
|
||||
function ADSupplyPlanner.isBetterSource(level, bestLevel, prefersFullest)
|
||||
-- Lagervarer: mindst fyldte først, men kun blandt rigelige kilder — en næsten tom tank der fyldes løbende
|
||||
-- (gæringssilo) ville ellers altid vinde og give et par tusind liter pr. tur (in-game 29/9). Ingen rigelige:
|
||||
-- den fyldeste. ample = nil: gammel regel.
|
||||
function ADSupplyPlanner.isBetterSource(level, bestLevel, prefersFullest, ample)
|
||||
if bestLevel == nil then
|
||||
return true
|
||||
end
|
||||
if prefersFullest then
|
||||
return level > bestLevel
|
||||
end
|
||||
return level < bestLevel
|
||||
if ample == nil then
|
||||
return level < bestLevel
|
||||
end
|
||||
local isAmple, bestIsAmple = level >= ample, bestLevel >= ample
|
||||
if isAmple ~= bestIsAmple then return isAmple end
|
||||
if isAmple then return level < bestLevel end
|
||||
return level > bestLevel
|
||||
end
|
||||
|
||||
function ADSupplyPlanner.copyList(list)
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<?xml version="1.0" encoding="utf-8" standalone="no"?>
|
||||
<modDesc descVersion="107">
|
||||
<author>masterdraco</author>
|
||||
<version>1.56.5.0</version>
|
||||
<version>1.57.0.0</version>
|
||||
<title>
|
||||
<en>AD Smart Pickup</en>
|
||||
</title>
|
||||
|
||||
@@ -206,9 +206,10 @@ check("markør uden nær silo ignoreres", manager:getNextPickup(makeDriver(marke
|
||||
|
||||
-- 4: flere valgte varer lægges sammen
|
||||
resetWorld()
|
||||
addMarker(1, "Silo 1", "Siloer", 0, 0); table.insert(stations, makeStation(101, 0, 15, {[SUGARBEET] = 100, [WHEAT] = 5000}))
|
||||
addMarker(2, "Silo 2", "Siloer", 500, 0); table.insert(stations, makeStation(102, 500, 15, {[SUGARBEET] = 3000}))
|
||||
check("flere varetyper summeres", manager:getNextPickup(makeDriver(markers[1], {SUGARBEET, WHEAT}), false), 2)
|
||||
-- summeret er silo 1 rigelig (6000 >= 5000) og vinder; uden summering var den 3000 og taber til silo 2's 4000
|
||||
addMarker(1, "Silo 1", "Siloer", 0, 0); table.insert(stations, makeStation(101, 0, 15, {[SUGARBEET] = 3000, [WHEAT] = 3000}))
|
||||
addMarker(2, "Silo 2", "Siloer", 500, 0); table.insert(stations, makeStation(102, 500, 15, {[SUGARBEET] = 4000}))
|
||||
check("flere varetyper summeres", manager:getNextPickup(makeDriver(markers[1], {SUGARBEET, WHEAT}), false), 1)
|
||||
|
||||
-- 4b: klynge med delt lager — eget indhold slår nabo-sum, også når nabo-summen er mindre
|
||||
resetWorld()
|
||||
|
||||
@@ -251,5 +251,16 @@ check("CF vare uden for run'et -> nil", ADSupplyPlanner.cargoFor(HAY, 5000, {SIL
|
||||
check("CF tom vogn -> nil", ADSupplyPlanner.cargoFor(SILAGE, 0, {SILAGE}), nil)
|
||||
check("CF ukendt vare -> nil", ADSupplyPlanner.cargoFor(nil, 5000, {SILAGE}), nil)
|
||||
|
||||
-- kilde med nok til et rigtigt læs: mindst fyldte først kun blandt kilder med >= 25 % af et læs; ellers fyldeste
|
||||
-- (in-game 29/9: 4 foder-traktorer hentede 2-10k l i en gæringssilo der løbende fyldes, og kørte "tomme")
|
||||
local SP = ADSupplyPlanner
|
||||
check("kilde-grænse: 25 % af læsset", SP.ampleLevel(1000000), 250000)
|
||||
check("kilde-grænse: ukendt læs -> kun minimum", SP.ampleLevel(nil), SP.MIN_AMPLE_LITERS)
|
||||
check("kilde-grænse: lille vogn -> mindst minimum", SP.ampleLevel(10000), SP.MIN_AMPLE_LITERS)
|
||||
check("vælg: næsten tom taber til rigelig", SP.isBetterSource(10000, 12000000, false, 250000), false)
|
||||
check("vælg: blandt rigelige mindst fyldte", SP.isBetterSource(300000, 12000000, false, 250000), true)
|
||||
check("vælg: ingen rigelige -> fyldeste", SP.isBetterSource(9000, 2000, false, 250000), true)
|
||||
check("vælg: løber-fuld-varer uændret (fyldeste)", SP.isBetterSource(12000000, 300000, true, 250000), true)
|
||||
check("vælg: første kandidat", SP.isBetterSource(10, nil, false, 250000), true)
|
||||
print(failures == 0 and "\nALLE TESTS OK" or ("\n" .. failures .. " FEJL"))
|
||||
os.exit(failures == 0 and 0 or 1)
|
||||
|
||||
Reference in New Issue
Block a user