group.cc
Go to the documentation of this file.
00001 /* group.cc
00002  */
00003 #include "osl/rating/group.h"
00004 #include "osl/rating/feature/karanari.h"
00005 #include "osl/rating/feature/pinAttack.h"
00006 #include <boost/filesystem/path.hpp>
00007 #include <boost/filesystem/operations.hpp>
00008 #include <iostream>
00009 #include <fstream>
00010 #include <sstream>
00011 #include <iomanip>
00012 #include <cstdio>
00013 #include <cmath>
00014 
00015 osl::rating::Group::Group(const std::string& name)
00016   : group_name(name)
00017 {
00018 }
00019 
00020 osl::rating::Group::~Group()
00021 {
00022 }
00023 
00024 int osl::rating::Group::findMatch(const NumEffectState& state, Move m, const RatingEnv& env) const
00025 {
00026   for (size_t j=0; j<size(); ++j) {
00027     if ((*this)[j].match(state, m, env)) 
00028       return j;
00029   }
00030   return -1;
00031 }
00032 
00033 void osl::rating::Group::saveResult(const std::string& directory, const range_t& range, 
00034                                     const vector<double>& weights) const
00035 {
00036   {
00037     boost::filesystem::path dir(directory);
00038     boost::filesystem::create_directory(dir);
00039   }
00040   
00041   std::string filename = directory + "/" + group_name + ".txt";
00042   std::ofstream os(filename.c_str());
00043   for (int i=range.first; i<range.second; ++i)
00044     os << std::setprecision(8) << weights[i] << "\n";
00045 }
00046 
00047 bool osl::rating::Group::load(const std::string& directory, const range_t& range, 
00048                               vector<double>& weights) const
00049 {  
00050   std::string filename = directory + "/" + group_name + ".txt";
00051   FILE *fp = fopen(filename.c_str(), "r");
00052   if (! fp)
00053     return false;
00054   for (int i=range.first; i<range.second; ++i) {
00055     if (fscanf(fp, "%lf", &weights[i]) != 1)
00056       return false;
00057   }
00058   fclose(fp);
00059   return true;
00060 }
00061 
00062 void osl::rating::Group::show(std::ostream& os, int name_width, const range_t& range, 
00063                               const vector<double>& weights) const
00064 {
00065 #ifndef MINIMAL
00066   for (size_t f=0; f<size(); ++f) {
00067     os << std::setw(name_width) 
00068        << (*this)[f].name() 
00069        << "  " << 400*log10(weights[f+range.first]) << "\n";
00070   }
00071 #endif
00072 }
00073 
00074 void osl::rating::Group::showAll(std::ostream& os, int name_width, const range_t& range, 
00075                                  const vector<double>& weights) const
00076 {
00077 #ifndef MINIMAL
00078   showMinMax(os, name_width, range, weights);
00079   for (size_t i=0; i<size(); ++i) {
00080     os << " " << (*this)[i].name() << " " << 400*log10(weights[i+range.first]);
00081   }
00082   os << "\n";
00083 #endif
00084 }
00085 void osl::rating::Group::showMinMax(std::ostream& os, int name_width, const range_t& range, 
00086                                     const vector<double>& weights) const 
00087 {
00088 #ifndef MINIMAL
00089   double min = 10000000000.0, max = -min;
00090   for (size_t i=0; i<size(); ++i) {
00091     min = std::min(min, 400*log10(weights[i+range.first]));
00092     max = std::max(max, 400*log10(weights[i+range.first]));
00093   }
00094   os << std::setw(name_width) 
00095      << group_name
00096      << "  [" << min << " -- " << max << "] ";
00097 #endif
00098 }
00099 
00100 void osl::rating::Group::showTopN(std::ostream& os, int name_width, const range_t& range, 
00101                                   const vector<double>& weights, int n) const
00102 {
00103 #ifndef MINIMAL
00104   if ((int)weights.size() <= n*2)
00105     return showAll(os, name_width, range, weights);
00106   showMinMax(os, name_width, range, weights);
00107   vector<double> w;
00108   w.reserve(size());
00109   for (int i=range.first; i<range.second; ++i)
00110     w.push_back(weights[i]);
00111   std::sort(w.begin(), w.end());
00112   for (int i=0; i<n; ++i) {
00113     double value = w[size()-1-i];
00114     int j=range.first;
00115     for (; j<range.second; ++j)
00116       if (weights[j] == value)
00117         break;
00118     os << " " << (*this)[j-range.first].name() << " " << 400*log10(value);
00119   }
00120   os << " ... ";
00121   for (int i=0; i<n; ++i) {
00122     double value = w[n-1-i];
00123     int j=range.first;
00124     for (; j<range.second; ++j)
00125       if (weights[j] == value)
00126         break;
00127     os << " " << (*this)[j-range.first].name() << " " << 400*log10(value);
00128   }  
00129   os << "\n";
00130 #endif
00131 }
00132 
00133 osl::rating::
00134 ChaseGroup::ChaseGroup() : Group("Chase")
00135 {
00136   for (int o=0; o<4; ++o) {
00137     for (int t=PTYPE_PIECE_MIN; t<=PTYPE_MAX; ++t) {
00138       Ptype target = static_cast<Ptype>(t);
00139       for (int s=PTYPE_PIECE_MIN; s<=PTYPE_MAX; ++s) {
00140         Ptype self = static_cast<Ptype>(s);
00141         push_back(new Chase(self, target, false, static_cast<Chase::OpponentType>(o)));
00142         if (isBasic(self))
00143           push_back(new Chase(self, target, true, static_cast<Chase::OpponentType>(o)));
00144       }      
00145     }
00146   }
00147 }
00148 
00149 int osl::rating::
00150 ChaseGroup::findMatch(const NumEffectState& state, Move move, const RatingEnv& env) const
00151 {
00152   Move last_move = env.history.lastMove();
00153   if (! last_move.isNormal())
00154     return -1;
00155   if (! state.hasEffectIf(move.ptypeO(), move.to(), last_move.to()))
00156     return -1;
00157   int base = 0;
00158   const int unit = (PTYPE_MAX+1 - PTYPE_PIECE_MIN)*(PTYPE_MAX+1-PTYPE_PIECE_MIN+PTYPE_MAX+1-PTYPE_BASIC_MIN);
00159   if (last_move.capturePtype() == PTYPE_EMPTY) {
00160     if (last_move.isDrop()) {
00161       base = unit;
00162     } else {
00163       if (state.hasEffectAt(state.turn(), last_move.from()))
00164         base = unit*2;
00165       else
00166         base = unit*3;
00167     }
00168   }
00169   Ptype self = move.ptype();
00170   Ptype target = last_move.ptype();
00171   int index = base + (target - PTYPE_PIECE_MIN)*(PTYPE_MAX+1-PTYPE_PIECE_MIN+PTYPE_MAX+1-PTYPE_BASIC_MIN);
00172   if (isBasic(self)) {
00173     index += (PTYPE_BASIC_MIN - PTYPE_PIECE_MIN);
00174     index += (self - PTYPE_BASIC_MIN)*2;
00175     index += move.isDrop();
00176   } else {
00177     index += (self - PTYPE_PIECE_MIN);
00178   }
00179   assert((*this)[index].match(state, move, env));
00180   return index;
00181 }
00182 
00183 osl::rating::KaranariGroup::KaranariGroup() : Group("Karanari")
00184 {
00185   push_back(new Karanari(false, true));
00186   push_back(new Karanari(false, false));
00187   push_back(new Karanari(true, true));
00188   push_back(new Karanari(true, false));
00189 }
00190 
00191 int osl::rating::
00192 KaranariGroup::findMatch(const NumEffectState& state, Move move, const RatingEnv&) const
00193 {
00194   return Karanari::index(state, move);
00195 }
00196 
00197 osl::rating::
00198 ImmediateAddSupportGroup::ImmediateAddSupportGroup() 
00199   : Group("ImmediateAddSupport")
00200 {
00201   for (int s=PTYPE_PIECE_MIN; s<=PTYPE_MAX; ++s) {
00202     for (int a=PTYPE_PIECE_MIN; a<=PTYPE_MAX; ++a) {
00203       for (int p=0; p<8; ++p)   // progress8
00204         push_back(new ImmediateAddSupport(static_cast<Ptype>(s), static_cast<Ptype>(a)));
00205     }
00206   }
00207 }
00208 
00209 /* ------------------------------------------------------------------------- */
00210 // ;;; Local Variables:
00211 // ;;; mode:c++
00212 // ;;; c-basic-offset:2
00213 // ;;; End:
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines