NOTE: All references to board positions such as free_parking, go_to_jail, etc. are strictly for comprehension. When writting actual code these would be replaced by a integer position in the space/board class. Also where money amounts are given it is assumed that these may change later on and only give an indication about an amount of money the AI wants to keep in its account. *********************************************************************** ** ** ** AI - Buy Property ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class property_value - attribute of property class "monopolies" - reference to attribute of property, possibly player class The AI buy property method first gets the integer representing the amount of cash the AI class has. If the AI doesn't have enough money to buy the property the method ends, otherwise some additional checks are made. First it is checked to see if the property is in the lower half of the board, meaning the less valuable properties from GO to FREE PARKING. If it is then it checks for whether it is really worth buying. It wants to have at least $100 left in its account and checks to see if it will give the AI a monopoly or keep another player from getting a monopoly. Basically precedence is given to the more expensive properties or if monopolies are involved. We don't want the AI to let other players take all monopolies if possible. public void AI_buy (int position, player_id) { get cash; if (cash > property_value) { if (position < free_parking) { if (((cash - prop_cost) >= 100) || player owns other properties of that color || another player owns other properties of that color) buy; else if ((position > free_parking) && (position < go_to_jail)) if (((cash - prop_cost) >= 25) || player owns other properties of that color || another player owns other properties of that color) buy; else if ((position > go_to_jail) && ((cash - prop_cost) >= 0)) buy; } } } *********************************************************************** ** ** ** AI - Buy House or Hotel ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class property_value - attribute of property class num_house - attribute of property class num_hotel - attribute of property class house_cost - attribute of property class hotel_cost - attribute of property class "monopoly" - attribute of property class, possibly player class The AI buys houses if and only if the number of houses on the given property position is less than 4 and if it has enough money. If there are already houses on the property then again if it has enough money it buys a hotel. Since the AI is supposed to be kind of "dumb" we don't worry about having a certain amount left over. Until its determined that this bankrupts the AI often the logic is that putting buildings on may lead to some big gains for the AI later on. public void AI_buy_house_hotel (int player_id, int position) { if (property is monopoly) get property_value for that monopoly; if (num_houses == 4) { get cash; if (cash - hotel_cost > 0) buy_hotel(); num_hotel++; } if (num_houses < 4) { get cash; if (cash - house_cost > 0) { buy_house(); num_house++; } } } *********************************************************************** ** ** ** AI - In jail trying to get out ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class in_jail - attribut of AI class get_out_of_jail_card - attribute of AI class try - Keeps track of number of trys AI has used to get out of jail When the AI is jailed it immediately checks for a get out of jail free card so that it can save money. If it doesn't have it but it does have enough money, rather than rolling, it pays the money so that it doesn't waste 3 turns while other players buy up property. If it doesn't have enough money then it rolls. If the roll is a double it immediately moves out jail and gets to roll again as stated in the rules. If it has used its three tries it immediately pays the $50 and may have to call the do_mortgage function to pay for it. public void AI_jailed (int player_id) { if (in_jail == TRUE) { if (get_out_of_jail_card > 0) { in_jail = FALSE; try = 0; } if ((cash > 50) || (try == 3)) { cash = cash - 50; in_jail = FALSE; try = 0; } else { if (try < 3) { roll(); if (roll() == doubles) { in_jail = FALSE; roll(); try = 0; } else try++; } if (try == 3) { do_mortgage(); cash = cash - 50; in_jail = FALSE; try = 0; } } } } *********************************************************************** ** ** ** AI - User Offers Trade to AI ** ** ** *********************************************************************** Attribute References: property_value - attribute of AI class "monopolies" - attribute of property class, possibly player class Right now the AI only takes trades for money and property, not property and property. This is only temporary and will be fixed. The way the descisions are made this time is if the monopoly to be traded is one of the AI's monopolies it flat refuses no matter what. Otherwise it compares the property_value with an amount over what its worth. If the value is acceptable the trade is performed otherwise the trade is declined. Again the more expensive properties have higher precendence over the lower priced ones. public void AI_they_trade (int player_id, int position, int amount) { if (position is monopoly) decline trade; else if (amount < property_value) decline trade; else if ((amount >= (property_value + 25)) && (position < free_parking)) trade; else if ((amount >= (property_value + 75)) && (position > free_parking)) trade; else decline trade; } *********************************************************************** ** ** ** AI - Offers Trade to User ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class set_amount - attribute of AI class that refers to an amount that should be left in bank account after trade "monopolies" - attribute of property class, possibly player class Our trade currently functions on a random number generator that has a one in four chance of offering a trade, so that users are no spammed with trade requests. If a trade is to be initiated a property that will finish one of our monopolies is found. The owner of that property is also found and if there is enough in our account to offer we offer the property_value plus 15 percent of what its worth. This works off a random number generator also. The AI will increase the asking amount by 15% between 1 and 3 times. public void AI_we_trade (int player_id, int position) { get random number between 0-3; if (number == 1) { check for 50% of a monopoly; get cash; find position of property we need; check user for that position; for (random number between 1 - 3) if ((position_owner != NULL) && (cash - (property_value + (.15 * value)) > set_amount)) offer trade with property_value + 15%; } } *********************************************************************** ** ** ** AI - Lifting Mortgages ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class mortgage_amount - attribute of property class set_amount - attribute of AI class that refers to an amount that should be left in bank account after trade The AI decides to lift mortgage based only on if there is enough money left in its account (set_amount attribute) before it will go ahead and mortgage a property. It will loop through all its mortgaged properties and do this as needed. public void AI_lift_mortgage (int amount) { access AI's mortgage record for (mortgaged properties) if ((cash - mortgage_amount) > set_amount) pay mortgage; } *********************************************************************** ** ** ** AI - Inherits User's Property and Must Decide When to Pay for it ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class mortgage_amount - attribute of property class prop_principal - It is still unclear what class will have this The AI is somewhat careful with paying of the principal of the properties it inherits. We want to keep quite a bit of money because if we're at the state in the game when people are going bankrupt we don't have to pay anymore than we have to. If it chooses not to pay it is forced to pay the 10% of all propertie costs it has inherited as set forth in the rules. public void AI_inherit (int mortgage_amount) { if (cash > (prop_principal + 300)) pay principal; else cash = cash - (mortgage_amount * .10); } *********************************************************************** ** ** ** AI - Mortgaging Property ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class mortgage_amount - attribute of property class "monopolies" - attribute of property class, possibly player class Definately the most complicated of the descisions the AI class has to make. First if it has no owned properties and no property to mortgage it is forced to return (probably into bankruptcy). The easiest implementation we could come up with is three arrays that will act like stacks. The AI will go through all of its non-monopoly, non-building properties from least valuable to most valuable and see if one can take care of the owed amount by itself. If not the property position will be pushed onto the property stack and its property value added to a running total. It will loop through all these non-monopoly, non-building properties in hopes of getting a big enough total to pay the debt. If this is done and a sufficient amount is not found then it will loop through all of the monopoly, non-building adding the values to the property stack. If enough is found all the properties on the stack are sold off. Next it checks for houses and hotels and adds their position to a stack for properties with houses and properties with hotels respectively. Each house or hotel cost for that property is then added to the total. Again if enough money is found all the houses in the houses stack are sold as well as the hotels on the hotel stack and properties on the property stack. Once all buildings are sold and the amount is not sufficient it then checks the monopolies that no longer have the buildings on them. public void AI_do_mortgage (int owed_amount) { if (prop_owned == 0 || property_not_mortgaged == 0) return; int total = 0; int property_position[28]; // owned by AI int house_position[28]; int hotel_position[28]; while (AI owns property && property not a monopoly) { if (mortgagevalue(position_of_property) >= owed_amount) mortgage(position_of_property); else { property_position[] = position_of_property; total = total + mortgagevalue(position_of_property); if (total >= owed_amount) { for ( all elements in property_position[] ) mortgage(position_of_property); } } } // end while while (AI owns property && property = monopoly) { Start at lowest properties and mortgage monopolys with no buildings if (price_of_house(position_of_property) * # of houses + total >= owed_amount) { sell_all_houses(position_of_property); for (all property_position[]) mortgage(position_of_property); } else if (price_of_hotel(position_of_property) + total >= owed_amount) { sell_hotel(position_of_property); for (all property_position[] && all house_position[]) { mortgage(position_of_property); sell_all_houses(position_of_property); } } Once all houses/hotels sold on particular monopoly, check to mortgage those properties before continuing to next monopoly. } //end while } //end function *********************************************************************** ** ** ** AI - Auction ** ** ** *********************************************************************** Attribute References: cash - attribute of AI class The AI follows much the same reasoning for auction as it does for trading. The more valuable the property the more likely the AI is to bid on it. If it has enough cash it will bet up to twice the value of the property. This may changed if the AI is out-bid a lot. public int AI_auction (int position, int highest_bid)\ { if (cash > highest_bid + 20) { if (property completes monopoly) return highest_bid + 20; else if ((position > free_parking < go_to_jail) && highest bid <= 2*proprty_value) return highest_bid +5; else if ((position > go_to_jail < go) && highest_bid <= 2*property_value) return highest_bid + 10; } }