pin.h Source File

- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
effect_util/pin.h
Go to the documentation of this file.
1 /* pin.h
2 */
3 #ifndef _PIN_H
4 #define _PIN_H
5
6 #include "osl/state/numEffectState.h"
7 #include "osl/container/pieceMask.h"
8 #include <boost/static_assert.hpp>
9 namespace osl
10 {
11 namespace effect_util
12 {
13
14 class PinOrOpen
15 {
16 private:
20 template <Player Defense,Direction DIR>
21 static void findDirectionStep(const NumEffectState& state, Square target,
22 PieceMask& pins, PieceMask const& onBoard)
23 {
24 const Offset offset = DirectionTraits<DIR>::blackOffset();
25 Square pos=target-offset;
26 int num;
27 while(Piece::isEmptyNum(num=state.pieceAt(pos).number()))
28 pos-=offset;
29 if(Piece::isEdgeNum(num)) return;
30 int num1=state.longEffectNumTable()[num][DIR];
31 if(Piece::isPieceNum(num1) && onBoard.test(num1)){
32 pins.set(num);
33 }
34 }
35 public:
36 template<Player Defense>
37 static PieceMask makeStep(const NumEffectState& state, Square target)
38 {
39 PieceMask pins;
40 PieceMask mask=state.piecesOnBoard(alt(Defense));
41 findDirectionStep<Defense,UL>(state,target,pins,mask);
42 findDirectionStep<Defense,U>(state,target,pins,mask);
43 findDirectionStep<Defense,UR>(state,target,pins,mask);
44 findDirectionStep<Defense,L>(state,target,pins,mask);
45 findDirectionStep<Defense,R>(state,target,pins,mask);
46 findDirectionStep<Defense,DL>(state,target,pins,mask);
47 findDirectionStep<Defense,D>(state,target,pins,mask);
48 findDirectionStep<Defense,DR>(state,target,pins,mask);
49 return pins;
50 }
51
52 static PieceMask makeStep(const NumEffectState& state, Square target,
53 Player defense)
54 {
55 if(defense==BLACK)
56 return makeStep<BLACK>(state,target);
57 else
58 return makeStep<WHITE>(state,target);
59 }
60 static PieceMask make(const NumEffectState& state,Player defense)
61 {
62 return makeStep(state,state.kingSquare<BLACK>(),defense);
63 }
64 };
69 class Pin
70 {
71 private:
72 template <Direction DIR>
73 static void findDirection(const SimpleState& state, Square target,
74 Player defense, PieceMask& pins)
75 {
76 const Offset diff = Board_Table.getOffset(defense, DIR);
77 const Piece pin = state.nextPiece(target, diff);
78 if(!pin.isOnBoardByOwner(defense)) return;
79 const Piece attack_piece = state.nextPiece(pin.square(), diff);
80 if(!attack_piece.isOnBoardByOwner(alt(defense))) return;
81 if (Ptype_Table.getMoveMask(attack_piece.ptype())
82 & DirectionTraits<DirectionTraits<DIR>::longDir>::mask)
83 pins.set(pin.number());
84 }
90 template<Player P>
91 static void findLance(const NumEffectState& state, Square target,
92 PieceMask& pins)
93 {
94 assert(target==state.kingSquare<P>());
95 const Offset diff = DirectionPlayerTraits<U,P>::offset();
96 Square pos = target+diff;
97 Piece pin;
98 while ((pin=state.pieceAt(pos)) == Piece::EMPTY())
99 pos += diff;
100 if (! pin.isOnBoardByOwner<P>() )
101 return;
102 NumBitmapEffect effect=state.effectSetAt(pos);
103 mask_t mask=(effect.getMask(1)&mask_t::makeDirect(PtypeFuns<LANCE>::indexMask<<8));
104 if(mask.any()){
105 pins.set(pin.number());
106 }
107 }
108 public:
113 static PieceMask makeNaive(const SimpleState& state, Square target,
114 Player defense);
115 private:
116 static bool hasEffectWithOffset(const SimpleState& state,
117 Piece attack_piece, Piece pin, Offset diff)
118 {
119 const Piece attack_piece2 = state.nextPiece(pin.square(), diff);
120 return attack_piece == attack_piece2;
121 }
122 static bool hasEffectWithOffset(const NumEffectState& state,
123 Piece attack_piece, Piece pin, Offset)
124 {
125 return state.hasEffectByPiece(attack_piece, pin.square());
126 }
127 static void findOffset(const NumEffectState& state,
128 Piece attack_piece, Square target,
129 Player defense, Offset diff, PieceMask& pins)
130 {
131 const Piece pin = state.nextPiece(target, diff);
132 assert(pin.isPiece());
133 if (pin.owner() != defense)
134 return;
135 if (! hasEffectWithOffset(state, attack_piece, pin, diff))
136 return;
137 pins.set(pin.number());
138 }
139 template <Ptype PTYPE>
140 static void findPtype(const NumEffectState& state, Square target,
141 Player attack, Player defense, PieceMask& result)
142 {
143 BOOST_STATIC_ASSERT((PTYPE == ROOK) || (PTYPE == BISHOP));
144 const PtypeO attack_ptypeo = newPtypeO(attack, PTYPE);
145 for (int i=PtypeTraits<PTYPE>::indexMin;
146 i < PtypeTraits<PTYPE>::indexLimit; ++i)
147 {
148 const Piece attack_piece = state.pieceOf(i);
149 if (attack_piece.isOnBoardByOwner(attack))
150 {
151 const Square attack_position = attack_piece.square();
152 const Offset32 diff(attack_position, target);
153 const EffectContent effect
154 = Ptype_Table.getEffect(attack_ptypeo, diff);
155 if (!effect.hasBlockableEffect()) // 利きはあるか
156 continue;
157 const Offset offset = effect.offset();
158 #if 0
159 if (offset.zero()) // 隣にいる場合: pin はない
160 continue;
161 #endif
162 findOffset(state, attack_piece, target, defense,
163 offset, result);
164 }
165 }
166 }
167 public:
172 static PieceMask makeByPiece(const NumEffectState& state, Square target,
173 Player defense);
174
179 static PieceMask makeByPieceKing(const NumEffectState& state, Square target,
180 Player defense);
181
185 template <Player Defense,Direction DIR>
186 static void findDirectionStep(const NumEffectState& state, Square target,
187 PieceMask& pins)
188 {
189 const Offset offset = DirectionTraits<DIR>::blackOffset();
190 Square pos=target-offset;
191 int num;
192 while(Piece::isEmptyNum(num=state.pieceAt(pos).number()))
193 pos-=offset;
194 if(Piece::isEdgeNum(num)) return;
195 if(Defense==BLACK){
196 if(!state.pieceAt(pos).pieceIsBlack()) return;
197 }
198 else{
199 if(state.pieceAt(pos).pieceIsBlack()) return;
200 }
201 int num1=state.longEffectNumTable()[num][DIR];
202 if(!Piece::isPieceNum(num1)) return;
203 if(Defense==BLACK){
204 if(!state.pieceOf(num1).pieceIsBlack())
205 pins.set(num);
206 }
207 else{
208 if(state.pieceOf(num1).pieceIsBlack())
209 pins.set(num);
210 }
211 }
212 template<Player Defense>
213 static PieceMask makeStep(const NumEffectState& state, Square target)
214 {
215 PieceMask pins;
216 findDirectionStep<Defense,UL>(state,target,pins);
217 findDirectionStep<Defense,U>(state,target,pins);
218 findDirectionStep<Defense,UR>(state,target,pins);
219 findDirectionStep<Defense,L>(state,target,pins);
220 findDirectionStep<Defense,R>(state,target,pins);
221 findDirectionStep<Defense,DL>(state,target,pins);
222 findDirectionStep<Defense,D>(state,target,pins);
223 findDirectionStep<Defense,DR>(state,target,pins);
224 return pins;
225 }
226
227 static PieceMask makeStep(const NumEffectState& state, Square target,
228 Player defense)
229 {
230 if(defense==BLACK)
231 return makeStep<BLACK>(state,target);
232 else
233 return makeStep<WHITE>(state,target);
234 }
235 template<Player Defense>
236 static PieceMask makeStep1(const NumEffectState& state, Square target)
237 {
238 PieceMask pins=PinOrOpen::makeStep<Defense>(state,target);;
239 pins &= state.piecesOnBoard(Defense);
240 return pins;
241 }
242
243 static PieceMask makeStep1(const NumEffectState& state, Square target,
244 Player defense)
245 {
246 if(defense==BLACK)
247 return makeStep1<BLACK>(state,target);
248 else
249 return makeStep1<WHITE>(state,target);
250 }
257 static PieceMask make(const NumEffectState& state, Square target,
258 Player defense)
259 {
260 return makeByPiece(state, target, defense);
261 }
265 static PieceMask make(const NumEffectState& state, Player defense)
266 {
267 return makeByPiece(state, defense);
268 }
269 static PieceMask makeNaive(const SimpleState& state, Player defense)
270 {
271 return makeNaive(state, state.kingSquare(defense), defense);
272 }
273 static PieceMask makeByPiece(const NumEffectState& state, Player defense)
274 {
275 return makeByPieceKing(state, state.kingSquare(defense), defense);
276 }
280 static int count(const NumEffectState& state, Player defense)
281 {
282 const PieceMask pins = make(state, defense);
283 return pins.countBit();
284 }
285 static int count(const NumEffectState& state, Square target,
286 Player defense)
287 {
288 const PieceMask pins = make(state, target, defense);
289 return pins.countBit();
290 }
291 };
292
293
294 } // namespace effect_util
295 } // namespace osl
296
297 #endif /* _PIN_H */
298 // ;;; Local Variables:
299 // ;;; mode:c++
300 // ;;; c-basic-offset:2
301 // ;;; End: