neighboring8Direct.h
Go to the documentation of this file.
00001 /* neighboring8Direct.h
00002  */
00003 #ifndef EFFECT_UTIL_NEIGHBORING8DIRECT_H
00004 #define EFFECT_UTIL_NEIGHBORING8DIRECT_H
00005 
00006 #include "osl/state/numEffectState.h"
00007 #include "osl/direction.h"
00008 
00009 namespace osl
00010 {
00011   namespace effect_util
00012   {
00016     class Neighboring8Direct
00017     {
00018       class Table
00019       {
00020         struct Entry
00021         {
00022           bool has_unblockable_effect;
00023           Offset nearest;
00024           Entry() : has_unblockable_effect(false), nearest(Offset::ZERO())
00025           {
00026           }
00027         };
00028         CArray2d<Entry,PTYPEO_SIZE,Offset32::SIZE> table;
00029         void init(Player);
00030       public:
00031         Table();
00032         bool hasEffect(const NumEffectState& state,
00033                        PtypeO ptypeo, Square from, 
00034                        Square target) const
00035         {
00036           const Offset32 offset32 = Offset32(target, from);
00037           const Entry& e = table[ptypeOIndex(ptypeo)][offset32.index()];
00038           if (e.has_unblockable_effect)
00039             return true;
00040           if (e.nearest.zero())
00041             return false;
00042           assert(Ptype_Table.hasLongMove(getPtype(ptypeo)));
00043           const Square nearest = from+e.nearest;
00044           if (nearest.isEdge())
00045           {
00046             return false;
00047           }
00048           return state.isEmptyBetween(from, nearest, false);
00049         }
00050         bool hasEffectOrAdditional(const NumEffectState& state,
00051                                    PtypeO ptypeo, Square from, 
00052                                    Square target) const
00053         {
00054           const Offset32 offset32 = Offset32(target, from);
00055           const Entry& e = table[ptypeOIndex(ptypeo)][offset32.index()];
00056           if (e.has_unblockable_effect)
00057             return true;
00058           if (e.nearest.zero())
00059             return false;
00060           assert(Ptype_Table.hasLongMove(getPtype(ptypeo)));
00061           const Square nearest = from+e.nearest;
00062           if (nearest.isEdge())
00063           {
00064             return false;
00065           }
00066           Offset offset=Board_Table.getShortOffset(Offset32(nearest,from));
00067           assert(! offset.zero());
00068           Square pos=from+offset;
00069           Piece p = state.pieceAt(pos);
00070           for (; p.isEmpty(); pos+=offset, p=state.pieceAt(pos)) {
00071             if (pos==nearest)
00072               return true;
00073           }
00074           assert(p.isPiece());
00075           if (pos == nearest || state.hasEffectByPiece(p, nearest))
00076             return true;
00077           const Player attack = getOwner(ptypeo);
00078           if (target != state.kingSquare(alt(attack)))
00079             return false;
00080           // new pin?
00081           const Direction dir = longToShort(Board_Table.getLongDirection(attack,Offset32(nearest, from)));
00082           return pos == state.kingMobilityOfPlayer(alt(attack), dir);
00083         }
00084         Square findNearest(const NumEffectState& state,
00085                              PtypeO ptypeo, Square from, 
00086                              Square target) const
00087         {
00088           const Offset32 offset32 = Offset32(target, from);
00089           const Entry& e = table[ptypeOIndex(ptypeo)][offset32.index()];
00090           if (e.has_unblockable_effect)
00091             return from;
00092           if (e.nearest.zero())
00093             return Square::STAND();
00094           assert(Ptype_Table.hasLongMove(getPtype(ptypeo)));
00095           const Square nearest = from+e.nearest;
00096           if (!nearest.isEdge() && state.isEmptyBetween(from, nearest, false))
00097             return nearest;
00098           return Square::STAND();
00099         }
00100       };
00101       static const Table table;
00102     public:
00106       static bool hasEffect(const NumEffectState& state,
00107                             PtypeO ptypeo, Square from, 
00108                             Square target)
00109       {
00110         return table.hasEffect(state, ptypeo, from, target);
00111       }
00116       static bool hasEffectOrAdditional(const NumEffectState& state,
00117                                         PtypeO ptypeo, Square from, 
00118                                         Square target)
00119       {
00120         return table.hasEffectOrAdditional(state, ptypeo, from, target);
00121       }
00122       static Square findNearest(const NumEffectState& state,
00123                                   PtypeO ptypeo, Square from, 
00124                                   Square target)
00125       {
00126         return table.findNearest(state, ptypeo, from, target);
00127       }
00128     private:
00129       static bool hasEffectFromTo(const NumEffectState& state,
00130                                   PtypeO ptypeo, Square from, 
00131                                   Square target, Direction d);
00132     public:
00133       static bool hasEffectNaive(const NumEffectState& state,
00134                                  PtypeO ptypeo, Square from, 
00135                                  Square target);
00136     };
00137 
00138   } // namespace effect_util
00139   using effect_util::Neighboring8Direct;
00140 } // namespace osl
00141 
00142 #endif /* EFFECT_UTIL_NEIGHBORING8DIRECT_H */
00143 // ;;; Local Variables:
00144 // ;;; mode:c++
00145 // ;;; c-basic-offset:2
00146 // ;;; End:
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines