use of games.strategy.triplea.ai.pro.data.ProPurchaseTerritory in project triplea by triplea-game.
the class ProBattleUtils method territoryHasLocalLandSuperiority.
public static boolean territoryHasLocalLandSuperiority(final Territory t, final int distance, final PlayerID player, final Map<Territory, ProPurchaseTerritory> purchaseTerritories) {
final GameData data = ProData.getData();
if (t == null) {
return true;
}
for (int i = 2; i <= distance; i++) {
// Find enemy strength
final Set<Territory> nearbyTerritoriesForEnemy = data.getMap().getNeighbors(t, i, ProMatches.territoryCanMoveLandUnits(player, data, false));
nearbyTerritoriesForEnemy.add(t);
final List<Unit> enemyUnits = new ArrayList<>();
for (final Territory nearbyTerritory : nearbyTerritoriesForEnemy) {
enemyUnits.addAll(nearbyTerritory.getUnits().getMatches(ProMatches.unitIsEnemyNotNeutral(player, data)));
}
// Find allied strength
final Set<Territory> nearbyTerritoriesForAllied = data.getMap().getNeighbors(t, i - 1, ProMatches.territoryCanMoveLandUnits(player, data, false));
nearbyTerritoriesForAllied.add(t);
final List<Unit> alliedUnits = new ArrayList<>();
for (final Territory nearbyTerritory : nearbyTerritoriesForAllied) {
alliedUnits.addAll(nearbyTerritory.getUnits().getMatches(Matches.isUnitAllied(player, data)));
}
for (final ProPurchaseTerritory purchaseTerritory : purchaseTerritories.values()) {
for (final ProPlaceTerritory ppt : purchaseTerritory.getCanPlaceTerritories()) {
if (nearbyTerritoriesForAllied.contains(ppt.getTerritory())) {
alliedUnits.addAll(ppt.getPlaceUnits());
}
}
}
// Determine strength difference
final double strengthDifference = estimateStrengthDifference(t, enemyUnits, alliedUnits);
ProLogger.trace(t + ", current enemy land strengthDifference=" + strengthDifference + ", distance=" + i + ", enemySize=" + enemyUnits.size() + ", alliedSize=" + alliedUnits.size());
if (strengthDifference > 50) {
return false;
}
}
return true;
}
use of games.strategy.triplea.ai.pro.data.ProPurchaseTerritory in project triplea by triplea-game.
the class ProPurchaseUtils method findPurchaseTerritories.
public static Map<Territory, ProPurchaseTerritory> findPurchaseTerritories(final PlayerID player) {
ProLogger.info("Find all purchase territories");
final GameData data = ProData.getData();
// Find all territories that I can place units on
final RulesAttachment ra = player.getRulesAttachment();
List<Territory> ownedAndNotConqueredFactoryTerritories;
if (ra != null && ra.getPlacementAnyTerritory()) {
ownedAndNotConqueredFactoryTerritories = data.getMap().getTerritoriesOwnedBy(player);
} else {
ownedAndNotConqueredFactoryTerritories = CollectionUtils.getMatches(data.getMap().getTerritories(), ProMatches.territoryHasInfraFactoryAndIsNotConqueredOwnedLand(player, data));
}
ownedAndNotConqueredFactoryTerritories = CollectionUtils.getMatches(ownedAndNotConqueredFactoryTerritories, ProMatches.territoryCanMoveLandUnits(player, data, false));
// Create purchase territory holder for each factory territory
final Map<Territory, ProPurchaseTerritory> purchaseTerritories = new HashMap<>();
for (final Territory t : ownedAndNotConqueredFactoryTerritories) {
final int unitProduction = getUnitProduction(t, data, player);
final ProPurchaseTerritory ppt = new ProPurchaseTerritory(t, data, player, unitProduction);
purchaseTerritories.put(t, ppt);
ProLogger.debug(ppt.toString());
}
return purchaseTerritories;
}
use of games.strategy.triplea.ai.pro.data.ProPurchaseTerritory in project triplea by triplea-game.
the class ProPurchaseUtils method removeInvalidPurchaseOptions.
public static List<ProPurchaseOption> removeInvalidPurchaseOptions(final PlayerID player, final GameData data, final List<ProPurchaseOption> purchaseOptions, final ProResourceTracker resourceTracker, final int remainingUnitProduction, final List<Unit> unitsToPlace, final Map<Territory, ProPurchaseTerritory> purchaseTerritories) {
for (final Iterator<ProPurchaseOption> it = purchaseOptions.iterator(); it.hasNext(); ) {
final ProPurchaseOption purchaseOption = it.next();
// Check PU cost and production
if (!resourceTracker.hasEnough(purchaseOption) || purchaseOption.getQuantity() > remainingUnitProduction) {
it.remove();
continue;
}
// Check max unit limits (-1 is unlimited)
final int maxBuilt = purchaseOption.getMaxBuiltPerPlayer();
final UnitType type = purchaseOption.getUnitType();
if (maxBuilt == 0) {
it.remove();
} else if (maxBuilt > 0) {
// Find number of unit type that are already built and about to be placed
int currentlyBuilt = 0;
final Predicate<Unit> unitTypeOwnedBy = Matches.unitIsOfType(type).and(Matches.unitIsOwnedBy(player));
final List<Territory> allTerritories = data.getMap().getTerritories();
for (final Territory t : allTerritories) {
currentlyBuilt += t.getUnits().countMatches(unitTypeOwnedBy);
}
currentlyBuilt += CollectionUtils.countMatches(unitsToPlace, unitTypeOwnedBy);
for (final ProPurchaseTerritory t : purchaseTerritories.values()) {
for (final ProPlaceTerritory placeTerritory : t.getCanPlaceTerritories()) {
currentlyBuilt += CollectionUtils.countMatches(placeTerritory.getPlaceUnits(), unitTypeOwnedBy);
}
}
final int allowedBuild = maxBuilt - currentlyBuilt;
if (allowedBuild - purchaseOption.getQuantity() < 0) {
it.remove();
}
}
}
return purchaseOptions;
}
use of games.strategy.triplea.ai.pro.data.ProPurchaseTerritory in project triplea by triplea-game.
the class ProAi method purchase.
@Override
protected void purchase(final boolean purchaseForBid, final int pusToSpend, final IPurchaseDelegate purchaseDelegate, final GameData data, final PlayerID player) {
final long start = System.currentTimeMillis();
BattleCalculator.clearOolCache();
ProLogUi.notifyStartOfRound(data.getSequence().getRound(), player.getName());
initializeData();
if (pusToSpend <= 0) {
return;
}
if (purchaseForBid) {
calc.setData(data);
storedPurchaseTerritories = purchaseAi.bid(pusToSpend, purchaseDelegate, data);
} else {
// Repair factories
purchaseAi.repair(pusToSpend, purchaseDelegate, data, player);
// Check if any place territories exist
final Map<Territory, ProPurchaseTerritory> purchaseTerritories = ProPurchaseUtils.findPurchaseTerritories(player);
final List<Territory> possibleFactoryTerritories = CollectionUtils.getMatches(data.getMap().getTerritories(), ProMatches.territoryHasNoInfraFactoryAndIsNotConqueredOwnedLand(player, data));
if (purchaseTerritories.isEmpty() && possibleFactoryTerritories.isEmpty()) {
ProLogger.info("No possible place or factory territories owned so exiting purchase logic");
return;
}
ProLogger.info("Starting simulation for purchase phase");
// Setup data copy and delegates
GameData dataCopy;
try {
data.acquireReadLock();
dataCopy = GameDataUtils.cloneGameData(data, true);
} catch (final Throwable t) {
ProLogger.log(Level.WARNING, "Error trying to clone game data for simulating phases", t);
return;
} finally {
data.releaseReadLock();
}
calc.setData(dataCopy);
final PlayerID playerCopy = dataCopy.getPlayerList().getPlayerId(player.getName());
final IMoveDelegate moveDel = DelegateFinder.moveDelegate(dataCopy);
final IDelegateBridge bridge = new ProDummyDelegateBridge(this, playerCopy, dataCopy);
moveDel.setDelegateBridgeAndPlayer(bridge);
// Determine turn sequence
final List<GameStep> gameSteps = new ArrayList<>();
for (final GameStep gameStep : dataCopy.getSequence()) {
gameSteps.add(gameStep);
}
// Simulate the next phases until place/end of turn is reached then use simulated data for purchase
final int nextStepIndex = dataCopy.getSequence().getStepIndex() + 1;
for (int i = nextStepIndex; i < gameSteps.size(); i++) {
final GameStep step = gameSteps.get(i);
if (!playerCopy.equals(step.getPlayerId())) {
continue;
}
dataCopy.getSequence().setRoundAndStep(dataCopy.getSequence().getRound(), step.getDisplayName(), step.getPlayerId());
final String stepName = step.getName();
ProLogger.info("Simulating phase: " + stepName);
if (stepName.endsWith("NonCombatMove")) {
ProData.initializeSimulation(this, dataCopy, playerCopy);
final Map<Territory, ProTerritory> factoryMoveMap = nonCombatMoveAi.simulateNonCombatMove(moveDel);
if (storedFactoryMoveMap == null) {
storedFactoryMoveMap = ProSimulateTurnUtils.transferMoveMap(factoryMoveMap, data, player);
}
} else if (stepName.endsWith("CombatMove") && !stepName.endsWith("AirborneCombatMove")) {
ProData.initializeSimulation(this, dataCopy, playerCopy);
final Map<Territory, ProTerritory> moveMap = combatMoveAi.doCombatMove(moveDel);
if (storedCombatMoveMap == null) {
storedCombatMoveMap = ProSimulateTurnUtils.transferMoveMap(moveMap, data, player);
}
} else if (stepName.endsWith("Battle")) {
ProData.initializeSimulation(this, dataCopy, playerCopy);
ProSimulateTurnUtils.simulateBattles(dataCopy, playerCopy, bridge, calc);
} else if (stepName.endsWith("Place") || stepName.endsWith("EndTurn")) {
ProData.initializeSimulation(this, dataCopy, player);
storedPurchaseTerritories = purchaseAi.purchase(purchaseDelegate, data);
break;
} else if (stepName.endsWith("Politics")) {
ProData.initializeSimulation(this, dataCopy, player);
final PoliticsDelegate politicsDelegate = DelegateFinder.politicsDelegate(dataCopy);
politicsDelegate.setDelegateBridgeAndPlayer(bridge);
final List<PoliticalActionAttachment> actions = politicsAi.politicalActions();
if (storedPoliticalActions == null) {
storedPoliticalActions = actions;
}
}
}
}
ProLogger.info(player.getName() + " time for purchase=" + (System.currentTimeMillis() - start));
}
use of games.strategy.triplea.ai.pro.data.ProPurchaseTerritory in project triplea by triplea-game.
the class ProPurchaseAi method place.
void place(final Map<Territory, ProPurchaseTerritory> purchaseTerritories, final IAbstractPlaceDelegate placeDelegate) {
ProLogger.info("Starting place phase");
data = ProData.getData();
player = ProData.getPlayer();
territoryManager = new ProTerritoryManager(calc);
if (purchaseTerritories != null) {
// Place all units calculated during purchase phase (land then sea to reduce failed placements)
for (final ProPurchaseTerritory t : purchaseTerritories.values()) {
for (final ProPlaceTerritory ppt : t.getCanPlaceTerritories()) {
if (!ppt.getTerritory().isWater()) {
final List<Unit> unitsToPlace = new ArrayList<>();
for (final Unit placeUnit : ppt.getPlaceUnits()) {
for (final Unit myUnit : player.getUnits()) {
if (myUnit.getType().equals(placeUnit.getType()) && !unitsToPlace.contains(myUnit)) {
unitsToPlace.add(myUnit);
break;
}
}
}
doPlace(data.getMap().getTerritory(ppt.getTerritory().getName()), unitsToPlace, placeDelegate);
ProLogger.debug(ppt.getTerritory() + " placed units: " + unitsToPlace);
}
}
}
for (final ProPurchaseTerritory t : purchaseTerritories.values()) {
for (final ProPlaceTerritory ppt : t.getCanPlaceTerritories()) {
if (ppt.getTerritory().isWater()) {
final List<Unit> unitsToPlace = new ArrayList<>();
for (final Unit placeUnit : ppt.getPlaceUnits()) {
for (final Unit myUnit : player.getUnits()) {
if (myUnit.getType().equals(placeUnit.getType()) && !unitsToPlace.contains(myUnit)) {
unitsToPlace.add(myUnit);
break;
}
}
}
doPlace(data.getMap().getTerritory(ppt.getTerritory().getName()), unitsToPlace, placeDelegate);
ProLogger.debug(ppt.getTerritory() + " placed units: " + unitsToPlace);
}
}
}
}
// Place remaining units (currently only implemented to handle land units, ex. WW2v3 China)
if (player.getUnits().getUnits().isEmpty()) {
return;
}
// Current data at the start of place
ProLogger.debug("Remaining units to place: " + player.getUnits().getUnits());
// Find all place territories
final Map<Territory, ProPurchaseTerritory> placeNonConstructionTerritories = ProPurchaseUtils.findPurchaseTerritories(player);
// Determine max enemy attack units and current allied defenders
findDefendersInPlaceTerritories(placeNonConstructionTerritories);
// Prioritize land territories that need defended and place additional defenders
final List<ProPlaceTerritory> needToDefendLandTerritories = prioritizeTerritoriesToDefend(placeNonConstructionTerritories, true);
placeDefenders(placeNonConstructionTerritories, needToDefendLandTerritories, placeDelegate);
// Find strategic value for each territory
ProLogger.info("Find strategic value for place territories");
final Map<Territory, Double> territoryValueMap = ProTerritoryValueUtils.findTerritoryValues(player, new ArrayList<>(), new ArrayList<>());
for (final ProPurchaseTerritory t : placeNonConstructionTerritories.values()) {
for (final ProPlaceTerritory ppt : t.getCanPlaceTerritories()) {
ppt.setStrategicValue(territoryValueMap.get(ppt.getTerritory()));
ProLogger.debug(ppt.getTerritory() + ", strategicValue=" + territoryValueMap.get(ppt.getTerritory()));
}
}
// Prioritize land place territories, add all territories, and then place units
final List<ProPlaceTerritory> prioritizedLandTerritories = prioritizeLandTerritories(placeNonConstructionTerritories);
for (final ProPurchaseTerritory ppt : placeNonConstructionTerritories.values()) {
for (final ProPlaceTerritory placeTerritory : ppt.getCanPlaceTerritories()) {
final Territory t = placeTerritory.getTerritory();
if (!t.isWater() && !prioritizedLandTerritories.contains(placeTerritory)) {
prioritizedLandTerritories.add(placeTerritory);
}
}
}
// Place regular land units
placeLandUnits(prioritizedLandTerritories, placeDelegate, false);
// Place isConstruction land units (needs separated since placeDelegate.getPlaceableUnits doesn't handle combined)
placeLandUnits(prioritizedLandTerritories, placeDelegate, true);
}
Aggregations