📄 betterpixie.java
字号:
package com.sillysoft.lux.agent;import com.sillysoft.lux.*;import com.sillysoft.lux.util.*;//// BetterPixie.java// Lux//// Copyright (c) 2002-2007 Sillysoft Games. // http://sillysoft.net// lux@sillysoft.net//// This source code is licensed free for non-profit purposes. // For other uses please contact lux@sillysoft.net////// BetterPixie builds a concrete agent out of SmartAgentBase to do the following...//// She picks countries in continents that have the fewest border points//// At the start of each turn (inside placeArmies) she decides what continents she will expend effort on.// Then she will place and attack from those continents.//// Also she tries to get a card every turn// She also runs attackHogWild()//// When fortifying she will fort to the borders of continents that are on the front lines.//import java.util.Random;import java.util.List;import java.util.List;import java.util.ArrayList;public class BetterPixie extends SmartAgentBase{float outnumberBy = 1; // for individual country attacksprotected int borderForce = 20;boolean[] ourConts; // whether we will spend efforts taking/holding each continentpublic String name() { return "BetterPixie"; }public float version() { return 1.0f; }public String description() { return "BetterPixie is a lovable little sprite. She enjoys kicking your ass."; }public void cardsPhase( Card[] cards ) { super.cardsPhase(cards); cashCardsIfPossible(cards); }public int pickCountry() { // our first choice is the continent with the least # of borders that is totally empty if (goalCont == -1) { setGoalToLeastBordersCont(); } // so now we have picked a cont... return pickCountryInContinent(goalCont); }// This method is a hook that EvilPixie uses to place better during hogwildboolean placeHogWild(int numberOfArmies) { return false; }// returns true if we want at least one continentboolean setupOurConts(int numberOfArmies) { if (ourConts == null) ourConts = new boolean[numContinents]; // calculate the armies needed to conquer each continent int[] neededForCont = new int[numContinents]; for (int i = 0; i < numContinents; i++) { neededForCont[i] = BoardHelper.getEnemyArmiesInContinent(ID, i, countries); // enemies in the cont neededForCont[i] *= 1.3; // add a multiple for losses int ourArmiesNearCont = BoardHelper.getPlayerArmiesInContinent(ID, i, countries) + BoardHelper.getPlayerArmiesAdjoiningContinent(ID, i, countries); // If we have a big group near the continent then consider that as well CountryRoute bestRoute = new CountryRoute(BoardHelper.cheapestRouteFromOwnerToCont(ID, i, countries), countries); int ourArmiesFartherAway = bestRoute.start().getArmies() - (int)(bestRoute.costNotCountingPlayer(ID)*1.2); neededForCont[i] -= Math.max(ourArmiesNearCont, ourArmiesFartherAway); } // We will only concentrate on the easiest continent to take when we own none boolean ownNoContinents = ! BoardHelper.playerOwnsAnyPositiveContinent(ID, countries, board); int lowestArmiesNeededToTake = 1000000; int targetCont = -1; boolean wantACont = false; // if we think we can take/hold any continents for (int i = 0; i < numContinents; i++) { if (ownNoContinents) { if (neededForCont[i] < lowestArmiesNeededToTake && board.getContinentBonus(i) > 0) { lowestArmiesNeededToTake = neededForCont[i]; targetCont = i; } ourConts[i] = false; } // say we can give at most numberOfArmies/(numContinents/4) armies to each continent. else if (neededForCont[i] < numberOfArmies/(numContinents/4.0) && board.getContinentBonus(i) > 0) { ourConts[i] = true; wantACont = true; } else ourConts[i] = false; } if (ownNoContinents) { if (targetCont == -1) return false; ourConts[targetCont] = true; return true; } return wantACont; }public void placeArmies( int numberOfArmies ) { if (placeHogWild(numberOfArmies)) return; // Calculate what continents we can take/hold if (! setupOurConts(numberOfArmies)) { // then we don't think we can take/hold any continents placeArmiesToTakeCont( numberOfArmies, getEasiestContToTake() ); return; } // divide our armies amongst the conts we want int armiesPlaced = 0; boolean oneNeedsHelp = true; while (armiesPlaced < numberOfArmies && oneNeedsHelp) { oneNeedsHelp = false; for (int c = 0; c < numContinents; c++) { if (ourConts[c] && continentNeedsHelp(c)) { debug("Placing an army to take continent "+board.getContinentName(c)); placeArmiesToTakeCont( 1, c ); armiesPlaced++; oneNeedsHelp = true; } } } // We place the dregs if all our borders are above borderforce. if (armiesPlaced < numberOfArmies) placeRemainder(numberOfArmies - armiesPlaced); }protected void placeRemainder(int numberOfArmies) { placeNearEnemies(numberOfArmies, true); }/** Place our armies so they are next to enemy clusters. If 'minimumToWin' is true then place the minimum number of armies needed to conquer each cluster (starting at the smallest). If 'minimumToWin' is false then place armies evenly for each cluster. */protected void placeNearEnemies(int numberOfArmies, boolean minimumToWin) { // Divide all enemy countries into clusters: List clustersWeBorder = new ArrayList(); CountryClusterSet clusters = CountryClusterSet.getAllCountriesNotOwnedBy(ID, countries); if (minimumToWin) clusters.orderWeakestFirst(); // Now place beside each enemy cluster for (int i = 0; i < clusters.size() && numberOfArmies > 0; i++) { CountryCluster cluster = clusters.getCluster(i); Country placeOn = cluster.getStrongestNeighborOwnedBy(ID); if (placeOn != null) { int numberToPlace = numberOfArmies/clusters.size(); if (minimumToWin) numberToPlace = cluster.estimatedNumberOfArmiesNeededToConquer() - placeOn.getArmies(); board.placeArmies(numberToPlace, placeOn); numberOfArmies -= numberToPlace; } } if (numberOfArmies > 0) { // we still have some left ? // This method is AWFUL!!! System.out.println("BetterPixie still has "+numberOfArmies+" left to place in a really bad manner"); // Thread.dumpStack(); int i = 0; while (numberOfArmies > 0) { if (countries[i].getOwner() == ID && countries[i].getNumberEnemyNeighbors() > 0) { board.placeArmies(1, i); numberOfArmies--; } i = (i+1)%numCountries; } } }boolean borderCountryNeedsHelp(Country border) { return border.getArmies() <= borderForce && ! weOwnContsArround(border); }// a test of whether or not we should send some armies this cont's wayprotected boolean continentNeedsHelp(int cont) { // if we don't own it then it definitely needs some help if (! BoardHelper.playerOwnsContinent(ID, cont, countries) ) return true; // otherwise we own it. // check each border int[] borders = BoardHelper.getContinentBorders(cont, countries); for (int i = 0; i < borders.length; i++) { if (borderCountryNeedsHelp(countries[ borders[i] ])) return true; } return false; }public void attackPhase( ) { // Try and take over all the continents we want for (int i = 0; i < numContinents; i++) { if (ourConts[i]) attackInContinent(i); } // Take out any badly defended conts next to us for (int i = 0; i < numContinents; i++) takeOutContinentCheck(i); attackForCard(); attackHogWild(); attackStalemate(); }// End of attackPhase// If we think we can take over this continent then execute lots of attacksprotected void attackInContinent( int cont ) { // Count the enemies and friendlies: int enemyCount = BoardHelper.getEnemyArmiesInContinent(ID, cont, countries); // enemies in the cont // add a multiple for losses and for the # of enemy countries
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -