BWAPI
Skynet/Skynet/ResourceManager.cpp
Go to the documentation of this file.
00001 #include "ResourceManager.h"
00002 #include "BaseTracker.h"
00003 #include "TaskManager.h"
00004 #include "GatherTask.h"
00005 #include "ResourceTracker.h"
00006 #include "BuildOrderManager.h"
00007 #include "UnitTracker.h"
00008 
00009 ResourceManagerClass::ResourceManagerClass()
00010         : mTaskPump(BWAPI::Broodwar->self()->getRace().getWorker(), TaskType::Worker)
00011         , mSaturated(false)
00012         , mGasLevel(0)
00013         , mTimeAllowGasChange(0)
00014 {
00015 }
00016 
00017 void ResourceManagerClass::update()
00018 {
00019         std::set<Base> bases = BaseTracker::Instance().getActiveBases(true);
00020         if(mMyActiveBases != bases)
00021         {
00022                 for each(Base base in mMyActiveBases)
00023                 {
00024                         std::set<Base>::iterator it = bases.find(base);
00025                         if(it == bases.end())
00026                         {
00027                                 for(std::map<Unit, GatherTaskPointer>::iterator resourceIT = mResourceTasks[base].begin(); resourceIT != mResourceTasks[base].end(); ++resourceIT)
00028                                         resourceIT->second->cancel();
00029 
00030                                 mResourceTasks.erase(base);
00031                         }
00032                 }
00033 
00034                 mMyActiveBases = bases;
00035         }
00036 
00037         unsigned int neededWorkers = 0;
00038         for each(Base base in mMyActiveBases)
00039         {
00040                 if(!base->getResourceDepot() || !base->getResourceDepot()->exists())
00041                         continue;
00042 
00043                 const UnitGroup &minerals = base->getMinerals();
00044                 const UnitGroup &refineries = base->getRefineries();
00045 
00046                 for(std::map<Unit, GatherTaskPointer>::iterator resourceIT = mResourceTasks[base].begin(); resourceIT != mResourceTasks[base].end();)
00047                 {
00048                         if(minerals.count(resourceIT->first) == 0 && refineries.count(resourceIT->first) == 0)
00049                         {
00050                                 resourceIT->second->cancel();
00051                                 mResourceToBase.erase(resourceIT->first);
00052                                 mResourceTasks[base].erase(resourceIT++);
00053                         }
00054                         else
00055                                 ++resourceIT;
00056                 }
00057 
00058                 for each(Unit mineral in minerals)
00059                 {
00060                         neededWorkers += 2;
00061                         if(mResourceTasks[base].count(mineral) == 0)
00062                         {
00063                                 GatherTaskPointer gatherTask(new GatherTask(mineral, base));
00064                                 TaskManager::Instance().addTask(gatherTask);
00065                                 mResourceTasks[base][mineral] = gatherTask;
00066                                 mResourceToBase[mineral] = base;
00067                         }
00068                 }
00069 
00070                 for each(Unit refinery in refineries)
00071                 {
00072                         if(refinery->getPlayer() == BWAPI::Broodwar->self())
00073                         {
00074                                 neededWorkers += 3;
00075                                 if(mResourceTasks[base].count(refinery) == 0 && refinery->exists())
00076                                 {
00077                                         GatherTaskPointer gatherTask(new GatherTask(refinery, base));
00078                                         TaskManager::Instance().addTask(gatherTask);
00079                                         mResourceTasks[base][refinery] = gatherTask;
00080                                         mResourceToBase[refinery] = base;
00081                                 }
00082                         }
00083                 }
00084         }
00085 
00086         if(!BuildOrderManager::Instance().getOrder(Order::TrainWorkers))
00087                 neededWorkers = 0;
00088 
00089         unsigned int numWorkers = UnitTracker::Instance().selectAllUnits(BWAPI::Broodwar->self()->getRace().getWorker()).size();
00090 
00091         mSaturated = numWorkers >= neededWorkers;
00092 
00093         neededWorkers = std::min(neededWorkers, 50u);
00094         neededWorkers -= std::min(numWorkers, neededWorkers);
00095         neededWorkers = std::min(neededWorkers, UnitTracker::Instance().selectAllUnits(BWAPI::Broodwar->self()->getRace().getWorker().whatBuilds().first).size() + 1);
00096 
00097         mTaskPump.changeTargetQuantity(neededWorkers);
00098         mTaskPump.update();
00099 
00100         double mineralRate = 0;
00101         double gasRate = 0;
00102         for(std::map<Base, std::map<Unit, GatherTaskPointer>>::iterator it = mResourceTasks.begin(); it != mResourceTasks.end(); ++it)
00103         {
00104                 for(std::map<Unit, GatherTaskPointer>::iterator it2 = it->second.begin(); it2 != it->second.end(); ++it2)
00105                 {
00106                         mineralRate += it2->second->getMineralRate();
00107                         gasRate += it2->second->getGasRate();
00108                 }
00109         }
00110 
00111         ResourceTracker::Instance().setMineralRate(mineralRate);
00112         ResourceTracker::Instance().setGasRate(gasRate);
00113 
00114         int futureMinerals = ResourceTracker::Instance().availableMineralAtTime(BWAPI::Broodwar->getFrameCount() + 450);
00115         int futureGas = ResourceTracker::Instance().availableGasAtTime(BWAPI::Broodwar->getFrameCount() + 450);
00116 
00117         if(mTimeAllowGasChange < BWAPI::Broodwar->getFrameCount())
00118         {
00119                 int newLevel = 0;
00120                 if(UnitTracker::Instance().selectAllUnits(BWAPI::Broodwar->self()->getRace().getRefinery()).size() == 0)
00121                         newLevel = 8;
00122                 else if(futureMinerals != 0)
00123                 {
00124                         float ratio = float(futureGas) / float(futureMinerals);
00125 
00126                         if(ratio > 2.5f)
00127                                 newLevel = 0;
00128                         else if(ratio > 1.9f)
00129                                 newLevel = 1;
00130                         else if(ratio > 1.3f)
00131                                 newLevel = 2;
00132                         else if(ratio > 1.0f)
00133                                 newLevel = 3;
00134                         else if(ratio > 0.95f)
00135                                 newLevel = 4;
00136                         else if(ratio > 0.9f)
00137                                 newLevel = 5;
00138                         else if(ratio > 0.85f)
00139                                 newLevel = 6;
00140                         else if(ratio > 0.4f)
00141                                 newLevel = 7;
00142                         else
00143                                 newLevel = 8;
00144                 }
00145 
00146                 if(mGasLevel != newLevel)
00147                 {
00148                         mTimeAllowGasChange = BWAPI::Broodwar->getFrameCount() + 24;
00149                         if(mGasLevel > newLevel)
00150                                 --mGasLevel;
00151                         else if(newLevel > mGasLevel)
00152                                 ++mGasLevel;
00153                 }
00154         }
00155 }
00156 
00157 void ResourceManagerClass::onDestroy(Unit unit)
00158 {
00159         std::map<Unit, Base>::iterator baseIT = mResourceToBase.find(unit);
00160         if(baseIT != mResourceToBase.end())
00161         {
00162                 std::map<Unit, GatherTaskPointer>::iterator resourceIT = mResourceTasks[baseIT->second].find(unit);
00163                 if(resourceIT != mResourceTasks[baseIT->second].end())
00164                 {
00165                         resourceIT->second->cancel();
00166                         mResourceTasks[baseIT->second].erase(unit);
00167                         mResourceToBase.erase(baseIT);
00168                 }
00169         }
00170 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines