All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
majorPiece.cc
Go to the documentation of this file.
3 #include <boost/foreach.hpp>
4 #include <algorithm>
5 using osl::MultiInt;
6 
7 template <bool Opening, osl::Ptype MajorBasic>
10 
11 template <bool Opening, osl::Ptype MajorBasic>
12 void osl::eval::ml::
14 {
15  for (size_t i = 0; i < weights.dimension(); ++i)
16  {
17  table[i] = weights.value(i);
18  }
19 }
20 
21 
22 template <bool Opening>
24 
25 template <bool Opening>
26 void osl::eval::ml::
28 {
29  weight = weights.value(0);
30 }
31 
32 template <bool Opening>
33 int osl::eval::ml::RookPawn<Opening>::eval(const NumEffectState &state)
34 {
35  int result = 0;
36  for (int i = PtypeTraits<ROOK>::indexMin;
37  i < PtypeTraits<ROOK>::indexLimit;
38  ++i)
39  {
40  const Piece piece = state.pieceOf(i);
41  if (piece.isOnBoard() && !piece.square().canPromote(piece.owner()) &&
42  !state.isPawnMaskSet(piece.owner(), piece.square().x()))
43  {
44  if (piece.owner() == BLACK)
45  result += weight;
46  else
47  result -= weight;
48  }
49  }
50  return result;
51 }
52 
53 
59 
60 void osl::eval::ml::
61 RookPawnYX::setUp(const Weights &weights)
62 {
63  for (int i = 0; i < ONE_DIM; ++i)
64  {
65  for (int s=0; s<NStages; ++s)
66  {
67  RookPawnY::y_attack_table[i][s] = weights.value(i + ONE_DIM * 2 * s);
68  RookPawnY::y_defense_table[i][s] = weights.value(i + ONE_DIM * 2 * s + ONE_DIM);
69  }
70  }
71 }
72 
73 
74 void osl::eval::ml::
75 RookPawnY::setUp(const Weights &weights)
76 {
77  for (int i = 0; i < ONE_DIM; ++i)
78  {
79  for (int s=0; s<NStages; ++s)
80  table[i][s] = weights.value(i + ONE_DIM*s);
81  }
82 }
83 
85 RookPawnY::eval(const NumEffectState &state,
86  const CArray2d<int, 2, 9> &pawns)
87 {
89  const CArray<Square,2> kings = {{
90  state.kingSquare<BLACK>(),
91  state.kingSquare<WHITE>(),
92  }};
93  for (int i = PtypeTraits<ROOK>::indexMin;
94  i < PtypeTraits<ROOK>::indexLimit;
95  ++i)
96  {
97  const Piece piece = state.pieceOf(i);
98  if (piece.isOnBoard())
99  {
100  if (piece.owner() == BLACK)
101  {
102  const int pawn_y =
103  pawns[BLACK][piece.square().x() - 1];
104  result +=
105  table[index(piece, pawn_y)] +
106  y_attack_table[indexY(kings[WHITE], piece, pawn_y)] +
107  y_defense_table[indexY(kings[BLACK], piece, pawn_y)];
108  }
109  else
110  {
111  int y = pawns[WHITE][piece.square().x() - 1];
112  if (y != 0)
113  y = 10 - y;
114  result -=
115  table[index(piece, y)] +
116  y_attack_table[indexY(kings[BLACK], piece, y)] +
117  y_defense_table[indexY(kings[WHITE], piece, y)];
118  }
119  }
120  }
121  return result;
122 }
123 
124 
126 
127 void osl::eval::ml::
128 AllMajor::setUp(const Weights &weights,int stage)
129 {
130  weight[stage] = weights.value(0);
131 }
132 
133 
134 template <bool Opening>
136 
137 template <bool Opening>
138 void osl::eval::ml::
140 {
141  for (size_t i = 0; i < weights.dimension(); ++i)
142  {
143  table[i] = weights.value(i);
144  }
145 }
146 
147 template <bool Opening>
148 int osl::eval::ml::
150  const NumEffectState &state, Piece piece)
151 {
152  return piece.ptype() + (state.turn() == piece.owner() ? 0 : PTYPE_SIZE);
153 }
154 
155 template <bool Opening>
156 template <osl::Ptype PTYPE>
157 int osl::eval::ml::
158 MajorGoldSilverAttacked<Opening>::evalOne(const NumEffectState &state)
159 {
160  int result = 0;
161  for (int i = PtypeTraits<PTYPE>::indexMin;
162  i < PtypeTraits<PTYPE>::indexLimit;
163  ++i)
164  {
165  const Piece piece = state.pieceOf(i);
166  if (piece.isOnBoard() &&
167  state.hasEffectAt(alt(piece.owner()), piece.square()))
168  {
169  const int weight = table[index(state, piece)];
170  if (piece.owner() == BLACK)
171  result += weight;
172  else
173  result -= weight;
174  }
175  }
176  return result;
177 }
178 
179 template <bool Opening>
180 int osl::eval::ml::
181 MajorGoldSilverAttacked<Opening>::eval(const NumEffectState &state)
182 {
183  int result = 0;
184  result += evalOne<ROOK>(state);
185  result += evalOne<BISHOP>(state);
186  result += evalOne<GOLD>(state);
187  result += evalOne<SILVER>(state);
188 
189  return result;
190 }
191 
195 
206 
207 
208 template<osl::Player P>
209 inline
211  const NumEffectState& state,
212  Square rook,
213  Square myKing,
214  Square opKing,
215  Square up,
216  Square dp,
217  Square rp,
218  Square lp,
219  bool isP)
220 {
222  PtypeO uPtypeO=state.pieceAt(up).ptypeO();
223  PtypeO dPtypeO=state.pieceAt(dp).ptypeO();
224  PtypeO rPtypeO=state.pieceAt(rp).ptypeO();
225  PtypeO lPtypeO=state.pieceAt(lp).ptypeO();
226  if(P==WHITE){
227  uPtypeO=(PtypeO)(static_cast<int>(uPtypeO)^(~15));
228  dPtypeO=(PtypeO)(static_cast<int>(dPtypeO)^(~15));
229  rPtypeO=(PtypeO)(static_cast<int>(rPtypeO)^(~15));
230  lPtypeO=(PtypeO)(static_cast<int>(lPtypeO)^(~15));
231  up=up.rotate180EdgeOK();
232  dp=dp.rotate180EdgeOK();
233  rp=rp.rotate180EdgeOK();
234  lp=lp.rotate180EdgeOK();
235  rook=rook.rotate180();
236  myKing=myKing.rotate180();
237  opKing=opKing.rotate180();
238  }
239  assert((myKing.y()-dp.y())<(myKing.y()-up.y()));
240  assert((myKing.x()-lp.x())<(myKing.x()-rp.x()));
241  result+=attack_u[index1(opKing,up,uPtypeO,isP)]+
242  attack_d[index1(opKing,dp,dPtypeO,isP)]+
243  attack_l[index1(opKing,lp,lPtypeO,isP)]+
244  attack_r[index1(opKing,rp,rPtypeO,isP)]+
245  defense_u[index1(myKing,up,uPtypeO,isP)]+
246  defense_d[index1(myKing,dp,dPtypeO,isP)]+
247  defense_l[index1(myKing,lp,lPtypeO,isP)]+
248  defense_r[index1(myKing,rp,rPtypeO,isP)]+
249  attack_nospace[index2(opKing,rook,isP)]+
250  defense_nospace[index2(myKing,rook,isP)];
251  return result;
252 }
253 
255 RookEffectBase::eval(const NumEffectState &state)
256 {
257  const CArray<Square,2> kings = {{
258  state.kingSquare(BLACK),
259  state.kingSquare(WHITE),
260  }};
262  for (int i = PtypeTraits<ROOK>::indexMin; i < PtypeTraits<ROOK>::indexLimit;
263  ++i)
264  {
265  const Piece p = state.pieceOf(i);
266  if (! p.isOnBoard()) continue;
267  const Square pos=p.square();
268  Square up=state.mobilityOf(U,i);
269  Square dp=state.mobilityOf(D,i);
270  Square lp=state.mobilityOf(L,i);
271  Square rp=state.mobilityOf(R,i);
272  const bool isP=p.isPromoted();
273  if(p.owner()==BLACK)
274  result+=evalOne<BLACK>(state,pos,kings[0],kings[1],up,dp,rp,lp,isP);
275  else
276  result-=evalOne<WHITE>(state,pos,kings[1],kings[0],dp,up,lp,rp,isP);
277  }
278  return result;
279 }
280 
281 void osl::eval::ml::RookEffect::setUp(const Weights &weights,int stage)
282 {
283  for (size_t i = 0; i < ONE_DIM; ++i)
284  {
285  attack_table[i][stage] = weights.value(i);
286  defense_table[i][stage] = weights.value(i + ONE_DIM);
287  }
288 }
289 
291 {
292  for (size_t i = 0; i < 32; ++i)
293  {
294  for (int s=0; s<NStages; ++s)
295  RookEffectBase::piece_table[i][s] = weights.value(i + 32*s);
296  }
297 }
298 
299 void osl::eval::ml::
301 {
302  CArray<MultiInt, 19584> piece_attack_table;
303  CArray<MultiInt, 19584> piece_defense_table;
304  for (size_t i = 0; i < ONE_DIM; ++i)
305  {
306  for (int s=0; s<NStages; ++s)
307  {
308  piece_attack_table[i][s] = weights.value(i + ONE_DIM*2*s);
309  piece_defense_table[i][s] = weights.value(i + ONE_DIM*2*s + ONE_DIM);
310  }
311  }
312  for(int isP=0;isP<2;isP++)
313  for(int y_diff=-9;y_diff<=9;y_diff++)
314  for(int x_diff= -9;x_diff<=9;x_diff++){
315  int i2=index2(x_diff,y_diff,isP);
316  if(abs(x_diff)<9 && abs(y_diff)<9){
317  attack_nospace[i2]=
318  -(attack_table[index(abs(x_diff),y_diff,true,isP)]+
319  attack_table[index(abs(x_diff),y_diff,false,isP)]);
320  defense_nospace[i2]=
321  -(defense_table[index(abs(x_diff),y_diff,true,isP)]+
322  defense_table[index(abs(x_diff),y_diff,false,isP)]);
323  }
324  for(int ptypeo= PTYPEO_MIN;ptypeo<=PTYPEO_MAX;ptypeo++){
325  if(getPtype((PtypeO)ptypeo)==(int)PTYPE_EMPTY) continue;
326  int i1=index1(x_diff,y_diff,(PtypeO)ptypeo,isP);
327  int indexPieceH,indexPieceV;
328  int table_ptypeo=ptypeo;
329  if(getPtype((PtypeO)ptypeo)==PTYPE_EDGE) table_ptypeo=PTYPEO_EDGE;
330  if(getPtype((PtypeO)ptypeo)==PTYPE_EDGE || abs(x_diff)==9 || abs(y_diff)==9){
331  indexPieceH= 0+0+(PTYPEO_EDGE-PTYPEO_MIN)*17*9+4896+isP*9792;
332  indexPieceV= 0+0+(PTYPEO_EDGE-PTYPEO_MIN)*17*9+ isP*9792;
333  }
334  else{
335  indexPieceH= index0(abs(x_diff),-y_diff,(PtypeO)ptypeo,true,isP);
336  indexPieceV= index0(abs(x_diff),-y_diff,(PtypeO)ptypeo,false,isP);
337  }
338  attack_u[i1]=piece_attack_table[indexPieceV]+piece_table[table_ptypeo-PTYPEO_MIN];
339  defense_u[i1]=piece_defense_table[indexPieceV];
340  attack_d[i1]=piece_attack_table[indexPieceV]+piece_table[table_ptypeo-PTYPEO_MIN];
341  defense_d[i1]=piece_defense_table[indexPieceV];
342  if(abs(x_diff)<=8){
343  for(int y_diff_1=y_diff+1;y_diff_1<=8;y_diff_1++){
344  int i=index(abs(x_diff),y_diff_1,false,isP);
345  attack_u[i1]+=attack_table[i];
346  defense_u[i1]+=defense_table[i];
347  }
348  for(int y_diff_1=std::max(-8,y_diff);y_diff_1<=8;y_diff_1++){
349  int i=index(abs(x_diff),y_diff_1,false,isP);
350  attack_d[i1]-=attack_table[i];
351  defense_d[i1]-=defense_table[i];
352  }
353  }
354  attack_l[i1]=piece_attack_table[indexPieceH]+piece_table[table_ptypeo-PTYPEO_MIN];
355  defense_l[i1]=piece_defense_table[indexPieceH];
356  attack_r[i1]=piece_attack_table[indexPieceH]+piece_table[table_ptypeo-PTYPEO_MIN];
357  defense_r[i1]=piece_defense_table[indexPieceH];
358  if(abs(y_diff)<=8){
359  for(int x_diff_1=x_diff+1;x_diff_1<=8;x_diff_1++){
360  int i=index(abs(x_diff_1),y_diff,true,isP);
361  attack_r[i1]+=attack_table[i];
362  defense_r[i1]+=defense_table[i];
363  }
364  for(int x_diff_1=std::max(-8,x_diff);x_diff_1<=8;x_diff_1++){
365  int i=index(abs(x_diff_1),y_diff,true,isP);
366  attack_l[i1]-=attack_table[i];
367  defense_l[i1]-=defense_table[i];
368  }
369  }
370  }
371  }
372 }
373 
374 
375 
378 
380 {
381  for (size_t i = 0; i < ONE_DIM; ++i)
382  {
383  for (int s=0; s<NStages; ++s)
384  promote_defense_table[i][s] = weights.value(i + ONE_DIM*s);
385  }
386 }
387 
389 {
390  for (size_t i = 0; i < ONE_DIM; ++i)
391  {
392  for (int s=0; s<NStages; ++s)
394  weights.value(i + ONE_DIM*s);
395  }
396 }
397 
399 RookPromoteDefense::eval(const NumEffectState &state)
400 {
402  for (int i = PtypeTraits<ROOK>::indexMin;
403  i < PtypeTraits<ROOK>::indexLimit;
404  ++i){
405  const Piece rook = state.pieceOf(i);
406  if(rook.isOnBoardNotPromoted()){
407  if(rook.owner()==BLACK){
408  Square rookPos=rook.square();
409  if(rookPos.y()>=4){
410  Square pos=state.mobilityOf(U,i);
411  const Piece attacked = state.pieceAt(pos);
412  if (attacked.canMoveOn<BLACK>()){
413  const NumBitmapEffect effect = state.effectSetAt(pos);
414  if (effect.countEffect(WHITE) == 1){
415  PieceMask mask = effect & state.piecesOnBoard(WHITE);
416  const Piece effect_piece = state.pieceOf(mask.takeOneBit());
417  const int index = attacked.ptype() * 16 + effect_piece.ptype();
418  result += promote_defense_table[index];
419  if (effect_piece.ptype() == ROOK &&
420  effect_piece.square().x() != rookPos.x())
421  {
422  result +=
423  promote_defense_rook_table[
424  attacked.ptype() * 9 +
425  mobility::RookMobility::countHorizontalAll<BLACK>(state,
426  rook)];
427  }
428  }
429  }
430  }
431  }
432  else{
433  Square rookPos=rook.square();
434  if(rookPos.y()<=6){
435  Square pos=state.mobilityOf(D,i);
436  const Piece attacked = state.pieceAt(pos);
437  if (attacked.canMoveOn<WHITE>()){
438  const NumBitmapEffect effect = state.effectSetAt(pos);
439  if (effect.countEffect(BLACK) == 1){
440  PieceMask mask = effect & state.piecesOnBoard(BLACK);
441  const Piece effect_piece = state.pieceOf(mask.takeOneBit());
442  const int index = attacked.ptype() * 16 + effect_piece.ptype();
443  result -= promote_defense_table[index];
444  if (effect_piece.ptype() == ROOK &&
445  effect_piece.square().x() != rookPos.x())
446  {
447  result -=
448  promote_defense_rook_table[
449  attacked.ptype() * 9 +
450  mobility::RookMobility::countHorizontalAll<WHITE>(state,
451  rook)];
452  }
453  }
454  }
455  }
456  }
457  }
458  }
459  return result;
460 }
461 
462 
463 
477 
478 
479 template<osl::Player P>
480 inline
482  const NumEffectState& state,
483  Square bishop,
484  Square myKing,
485  Square opKing,
486  Square ulp,
487  Square urp,
488  Square dlp,
489  Square drp,
490  bool isP)
491 {
493  PtypeO ulPtypeO=state.pieceAt(ulp).ptypeO();
494  PtypeO urPtypeO=state.pieceAt(urp).ptypeO();
495  PtypeO dlPtypeO=state.pieceAt(dlp).ptypeO();
496  PtypeO drPtypeO=state.pieceAt(drp).ptypeO();
497  if(P==WHITE){
498  ulPtypeO=(PtypeO)(static_cast<int>(ulPtypeO)^(~15));
499  urPtypeO=(PtypeO)(static_cast<int>(urPtypeO)^(~15));
500  dlPtypeO=(PtypeO)(static_cast<int>(dlPtypeO)^(~15));
501  drPtypeO=(PtypeO)(static_cast<int>(drPtypeO)^(~15));
502  ulp=ulp.rotate180EdgeOK();
503  urp=urp.rotate180EdgeOK();
504  dlp=dlp.rotate180EdgeOK();
505  drp=drp.rotate180EdgeOK();
506  bishop=bishop.rotate180();
507  myKing=myKing.rotate180();
508  opKing=opKing.rotate180();
509  }
510  result+=attack_ul[index1(opKing,ulp,ulPtypeO,isP)]+
511  attack_ur[index1(opKing,urp,urPtypeO,isP)]+
512  attack_dl[index1(opKing,dlp,dlPtypeO,isP)]+
513  attack_dr[index1(opKing,drp,drPtypeO,isP)]+
514  defense_ul[index1(myKing,ulp,ulPtypeO,isP)]+
515  defense_ur[index1(myKing,urp,urPtypeO,isP)]+
516  defense_dl[index1(myKing,dlp,dlPtypeO,isP)]+
517  defense_dr[index1(myKing,drp,drPtypeO,isP)]+
518  attack_nospace[index2(opKing,bishop,isP)]+
519  defense_nospace[index2(myKing,bishop,isP)];
520  return result;
521 }
522 
524 BishopEffectBase::eval(const NumEffectState &state)
525 {
526  const CArray<Square,2> kings = {{
527  state.kingSquare(BLACK),
528  state.kingSquare(WHITE),
529  }};
530 
532  for (int i = PtypeTraits<BISHOP>::indexMin; i < PtypeTraits<BISHOP>::indexLimit;
533  ++i)
534  {
535  const Piece p = state.pieceOf(i);
536  if (! p.isOnBoard()) continue;
537  const Square pos=p.square();
538  Square ulp=state.mobilityOf(UL,i);
539  Square urp=state.mobilityOf(UR,i);
540  Square dlp=state.mobilityOf(DL,i);
541  Square drp=state.mobilityOf(DR,i);
542  const bool isP=p.isPromoted();
543  if(p.owner()==BLACK)
544  result+=evalOne<BLACK>(state,pos,kings[0],kings[1],ulp,urp,dlp,drp,isP);
545  else
546  result-=evalOne<WHITE>(state,pos,kings[1],kings[0],drp,dlp,urp,ulp,isP);
547  }
548  return result;
549 }
550 
551 void osl::eval::ml::BishopEffect::setUp(const Weights &weights,int stage)
552 {
553  for (size_t i = 0; i < ONE_DIM; ++i)
554  {
555  attack_table[i][stage] = weights.value(i);
556  defense_table[i][stage] = weights.value(i + ONE_DIM);
557  }
558 }
559 
561 {
562  for (size_t i = 0; i < 32; ++i)
563  {
564  for (int s=0; s<NStages; ++s)
565  BishopEffectBase::piece_table[i][s] = weights.value(i + 32*s);
566  }
567 }
568 
569 
570 void osl::eval::ml::
572 {
573  CArray<MultiInt, 19584> piece_attack_table;
574  CArray<MultiInt, 19584> piece_defense_table;
575  for (size_t i = 0; i < ONE_DIM; ++i)
576  {
577  for (int s=0; s<NStages; ++s)
578  {
579  piece_attack_table[i][s] = weights.value(i + ONE_DIM * 2 * s);
580  piece_defense_table[i][s] = weights.value(i + ONE_DIM * 2 * s + ONE_DIM);
581  }
582  }
583  for(int isP=0;isP<2;isP++)
584  for(int y_diff=-9;y_diff<=9;y_diff++)
585  for(int x_diff= -9;x_diff<=9;x_diff++){
586  int i2=index2(x_diff,y_diff,isP);
587  if(abs(x_diff)<9 && abs(y_diff)<9){
588  attack_nospace[i2]=
589  -(attack_table[index(x_diff,y_diff,true,isP)]+
590  attack_table[index(x_diff,y_diff,false,isP)]);
591  defense_nospace[i2]=
592  -(defense_table[index(x_diff,y_diff,true,isP)]+
593  defense_table[index(x_diff,y_diff,false,isP)]);
594  }
595  for(int ptypeo= PTYPEO_MIN;ptypeo<=PTYPEO_MAX;ptypeo++){
596  if(getPtype((PtypeO)ptypeo)==(int)PTYPE_EMPTY) continue;
597  int i1=index1(x_diff,y_diff,(PtypeO)ptypeo,isP);
598  int indexPieceUR,indexPieceUL;
599  int table_ptypeo=ptypeo;
600  if(getPtype((PtypeO)ptypeo)==PTYPE_EDGE) table_ptypeo=PTYPEO_EDGE;
601  if(getPtype((PtypeO)ptypeo)==PTYPE_EDGE || abs(x_diff)==9 || abs(y_diff)==9){
602  indexPieceUR= 0+0+(PTYPEO_EDGE-PTYPEO_MIN)*17*9+4896+isP*9792;
603  indexPieceUL= 0+0+(PTYPEO_EDGE-PTYPEO_MIN)*17*9+ isP*9792;
604  }
605  else{
606  indexPieceUR= index0(x_diff,y_diff,(PtypeO)ptypeo,true,isP);
607  indexPieceUL= index0(x_diff,y_diff,(PtypeO)ptypeo,false,isP);
608  }
609  attack_ul[i1]=piece_attack_table[indexPieceUL]+piece_table[table_ptypeo-PTYPEO_MIN];
610  defense_ul[i1]=piece_defense_table[indexPieceUL];
611  attack_dr[i1]=piece_attack_table[indexPieceUL]+piece_table[table_ptypeo-PTYPEO_MIN];
612  defense_dr[i1]=piece_defense_table[indexPieceUL];
613  {
614  int y_diff_1=y_diff+1, x_diff_1=x_diff-1;
615  for(;y_diff_1<=8 && x_diff_1>=-8;y_diff_1++,x_diff_1--){
616  if(std::abs(x_diff_1)<=8 && std::abs(y_diff_1)<=8){
617  int i=index(x_diff_1,y_diff_1,false,isP);
618  attack_ul[i1]+=attack_table[i];
619  defense_ul[i1]+=defense_table[i];
620  }
621  }
622  }
623  {
624  int y_diff_1=y_diff, x_diff_1=x_diff;
625  for(;y_diff_1<=8 && x_diff_1>=-8;y_diff_1++,x_diff_1--){
626  if(std::abs(x_diff_1)<=8 && std::abs(y_diff_1)<=8){
627  int i=index(x_diff_1,y_diff_1,false,isP);
628  attack_dr[i1]-=attack_table[i];
629  defense_dr[i1]-=defense_table[i];
630  }
631  }
632  }
633  attack_ur[i1]=piece_attack_table[indexPieceUR]+piece_table[table_ptypeo-PTYPEO_MIN];
634  defense_ur[i1]=piece_defense_table[indexPieceUR];
635  attack_dl[i1]=piece_attack_table[indexPieceUR]+piece_table[table_ptypeo-PTYPEO_MIN];
636  defense_dl[i1]=piece_defense_table[indexPieceUR];
637  {
638  int y_diff_1=y_diff+1, x_diff_1=x_diff+1;
639  for(;y_diff_1<=8 && x_diff_1<=8;y_diff_1++,x_diff_1++){
640  if(std::abs(x_diff_1)<=8 && std::abs(y_diff_1)<=8){
641  int i=index(x_diff_1,y_diff_1,true,isP);
642  attack_ur[i1]+=attack_table[i];
643  defense_ur[i1]+=defense_table[i];
644  }
645  }
646  }
647  {
648  int y_diff_1=y_diff, x_diff_1=x_diff;
649  for(;y_diff_1<=8 && x_diff_1<=8;y_diff_1++,x_diff_1++){
650  if(std::abs(x_diff_1)<=8 && std::abs(y_diff_1)<=8){
651  int i=index(x_diff_1,y_diff_1,true,isP);
652  attack_dl[i1]-=attack_table[i];
653  defense_dl[i1]-=defense_table[i];
654  }
655  }
656  }
657  }
658  }
659 }
660 
664 
666 {
667  for (size_t i = 0; i < ONE_DIM; ++i)
668  {
669  for (int s=0; s<NStages; ++s)
670  table[i][s] = weights.value(i + ONE_DIM*s);
671  }
672 }
673 
674 void osl::eval::ml::
676 {
677  for (size_t i = 0; i < ONE_DIM; ++i)
678  {
679  for (int s=0; s<NStages; ++s)
680  BishopHead::king_table[i][s] = weights.value(i + ONE_DIM*s);
681  }
682  for(int x_diff=0;x_diff<=8;x_diff++)
683  for(int y_diff=-8;y_diff<=8;y_diff++){
684  for(int i=0;i<32;i++)
685  BishopHead::king_table[(i*9+x_diff)*17+y_diff+8]+=BishopHead::table[i];
686  }
687  const PtypeO PTYPEO_EMPTY_R=newPtypeO(WHITE,PTYPE_EMPTY);
688  const PtypeO PTYPEO_EDGE_R=newPtypeO(BLACK,PTYPE_EDGE);
689  for(int x_diff=0;x_diff<=8;x_diff++)
690  for(int y_diff=-8;y_diff<=8;y_diff++){
691  BishopHead::king_table[(ptypeOIndex(PTYPEO_EMPTY_R)*9+x_diff)*17+y_diff+8]=
692  BishopHead::king_table[(ptypeOIndex(PTYPEO_EMPTY)*9+x_diff)*17+y_diff+8];
693  BishopHead::king_table[(ptypeOIndex(PTYPEO_EDGE_R)*9+x_diff)*17+y_diff+8]=
694  BishopHead::king_table[(ptypeOIndex(PTYPEO_EDGE)*9+x_diff)*17+y_diff+8];
695  }
696 }
697 
699 {
700  for (size_t i = 0; i < ONE_DIM; ++i)
701  {
702  for (int s=0; s<NStages; ++s)
703  BishopHead::x_table[i][s] = weights.value(i + ONE_DIM*s);
704  }
705 }
706 
708 BishopHead::eval(const NumEffectState &state)
709 {
711  for (int i = PtypeTraits<BISHOP>::indexMin;
712  i < PtypeTraits<BISHOP>::indexLimit;
713  ++i){
714  const Piece p = state.pieceOf(i);
715  if (p.isOnBoardNotPromoted()){
716  const Square pos=p.square();
717  if (p.owner() == BLACK){
718  if(pos.y()>=2){
720  if (!state.hasEffectAt(BLACK, up)){
721  const Square king = state.kingSquare(BLACK);
722  const PtypeO ptypeo = state.pieceAt(up).ptypeO();
723  const int index_k = indexK(BLACK, ptypeo,
724  std::abs(pos.x() - king.x()),
725  pos.y() - king.y());
726  result += king_table[index_k];
727  result += x_table[indexX<BLACK>(ptypeo, pos.x())];
728  }
729  }
730  }
731  else if(pos.y()<=8) {
733  if (!state.hasEffectAt(WHITE, up)){
734  const Square king = state.kingSquare(WHITE);
735  const PtypeO ptypeo = state.pieceAt(up).ptypeO();
736  const int index_k = indexK(WHITE, ptypeo,
737  std::abs(pos.x() - king.x()),
738  pos.y() - king.y());
739  result -= king_table[index_k];
740  result -= x_table[indexX<WHITE>(ptypeo, pos.x())];
741  }
742  }
743  }
744  }
745  return result;
746 }
747 
748 
750 
752 {
753  for (size_t i = 0; i < ONE_DIM; ++i)
754  {
755  for (int s=0; s<NStages; ++s)
756  table[i][s] = weights.value(i + ONE_DIM*s);
757  }
758 }
759 
760 template<osl::Player P>
762 KingRookBishop::evalOne(const NumEffectState &state)
763 {
764  const Square king=state.kingSquare(P);
766  for (int i = PtypeTraits<ROOK>::indexMin;
767  i < PtypeTraits<ROOK>::indexLimit;
768  ++i)
769  {
770  const Piece rook = state.pieceOf(i);
771  if (!rook.isOnBoard())
772  {
773  continue;
774  }
775  for (int j = PtypeTraits<BISHOP>::indexMin;
776  j < PtypeTraits<BISHOP>::indexLimit;
777  ++j)
778  {
779  const Piece bishop = state.pieceOf(j);
780  if (!bishop.isOnBoard())
781  {
782  continue;
783  }
784  result += table[index<P>(king, rook, bishop)];
785  }
786  }
787  return result;
788 }
789 
791 KingRookBishop::eval(const NumEffectState &state)
792 {
793  return evalOne<BLACK>(state)-evalOne<WHITE>(state);
794 }
795 
796 
800 
801 void osl::eval::ml::
803 {
804  for (size_t i = 0; i < ONE_DIM; ++i)
805  {
806  for (int s=0; s<NStages; ++s)
808  weights.value(i + ONE_DIM*s);
809  }
810 }
811 
812 void osl::eval::ml::
814 {
815  for (size_t i = 0; i < ONE_DIM; ++i)
816  {
817  for (int s=0; s<NStages; ++s)
819  weights.value(i + ONE_DIM*s);
820  }
821 }
822 
823 void osl::eval::ml::
825 {
826  for (size_t i = 0; i < ONE_DIM; ++i)
827  {
828  for (int s=0; s<NStages; ++s)
830  weights.value(i + ONE_DIM*s);
831  }
832 }
833 
835 NumPiecesBetweenBishopAndKing::eval(const NumEffectState &state)
836 {
838  for (int i = PtypeTraits<BISHOP>::indexMin;
839  i < PtypeTraits<BISHOP>::indexLimit;
840  ++i)
841  {
842  const Piece bishop = state.pieceOf(i);
843  if (!bishop.isOnBoard())
844  {
845  continue;
846  }
847  int self, opp, all;
848  countBetween(state,
849  state.kingSquare(alt(bishop.owner())),
850  bishop, self, opp, all);
851  if (bishop.owner() == BLACK)
852  {
853  result += (self_table[self] + opp_table[opp] + all_table[all]);
854  }
855  else
856  {
857  result -= (self_table[self] + opp_table[opp] + all_table[all]);
858  }
859  }
860  return result;
861 }
862 
863 void osl::eval::ml::
865  const NumEffectState &state, Square king, Piece bishop,
866  int &self_count, int &opp_count, int &total_count)
867 {
868  assert(bishop.isOnBoard());
869  if ((king.x() + king.y() != bishop.square().x() + bishop.square().y()) &&
870  (king.x() - king.y() != bishop.square().x() - bishop.square().y()))
871  {
872  self_count = opp_count = total_count = 8;
873  return;
874  }
875  Direction dir;
876  assert(king.x() != bishop.square().x());
877  assert(king.y() != bishop.square().y());
878  if (king.x() < bishop.square().x())
879  {
880  if (king.y() < bishop.square().y())
881  {
882  dir = UR;
883  }
884  else
885  {
886  dir = DR;
887  }
888  }
889  else
890  {
891  if (king.y() < bishop.square().y())
892  {
893  dir = UL;
894  }
895  else
896  {
897  dir = DL;
898  }
899  }
900  const Player player = bishop.owner();
901  const Direction move_dir = (player == BLACK ? dir : inverse(dir));
902  self_count = opp_count = total_count = 0;
903  for (Square pos = state.mobilityOf(dir, bishop.number());
904  pos != king; pos = Board_Table.nextSquare(player, pos, move_dir))
905  {
906  assert(pos.isOnBoard());
907  const Piece piece = state.pieceAt(pos);
908  if (!piece.isEmpty())
909  {
910  ++total_count;
911  if (piece.owner() == player)
912  ++self_count;
913  else
914  ++opp_count;
915  }
916  }
917 }
918 
919 
922 
923 void osl::eval::ml::
925 {
926  for (size_t i = 0; i < ONE_DIM; ++i)
927  {
928  for (int s=0; s<NStages; ++s)
929  table[i][s] = weights.value(i + ONE_DIM*s);
930  }
931 }
932 
934 BishopBishopPiece::eval(const NumEffectState &state)
935 {
937  const Piece bishop1 = state.pieceOf(PtypeTraits<BISHOP>::indexMin);
938  const Piece bishop2 = state.pieceOf(PtypeTraits<BISHOP>::indexMin + 1);
939  if (!bishop1.isOnBoard() || !bishop2.isOnBoard() ||
940  bishop1.owner() == bishop2.owner())
941  return result;
942  if (bishop1.square().x() + bishop1.square().y() !=
943  bishop2.square().x() + bishop2.square().y() &&
944  bishop1.square().x() - bishop1.square().y() !=
945  bishop2.square().x() - bishop2.square().y())
946  return result;
947 
948  if (state.hasEffectByPtype<BISHOP>(bishop2.owner(), bishop1.square()))
949  return result;
950 
951  Direction dir;
952  if (bishop1.square().x() < bishop2.square().x())
953  {
954  if (bishop1.square().y() < bishop2.square().y())
955  {
956  dir = UR;
957  }
958  else
959  {
960  dir = DR;
961  }
962  }
963  else
964  {
965  if (bishop1.square().y() < bishop2.square().y())
966  {
967  dir = UL;
968  }
969  else
970  {
971  dir = DL;
972  }
973  }
974  Square p1 = state.mobilityOf(inverse(dir), bishop1.number());
975  Square p2 = state.mobilityOf(dir, bishop2.number());
976  if (p1 == p2)
977  {
978  const Piece p = state.pieceAt(p1);
979  const bool black_with_support =
980  state.hasEffectAt<BLACK>(bishop1.owner() == BLACK ?
981  bishop1.square() : bishop2.square());
982  const bool white_with_support =
983  state.hasEffectAt<WHITE>(bishop1.owner() == WHITE ?
984  bishop1.square() : bishop2.square());
985  if (p.owner() == BLACK)
986  {
987  result += table[index(p.ptype(), black_with_support,
988  white_with_support)];
989  }
990  else
991  {
992  result -= table[index(p.ptype(), white_with_support,
993  black_with_support)];
994  }
995  }
996  return result;
997 }
998 
1001 
1002 void osl::eval::ml::
1003 RookRook::setUp(const Weights &weights)
1004 {
1005  CArray<MultiInt, 800> orig_table;
1006  for (size_t i = 0; i < ONE_DIM; ++i)
1007  {
1008  for (int s=0; s<NStages; ++s)
1009  orig_table[i][s] = weights.value(i + ONE_DIM*s);
1010  }
1011  for (int owner = 0; owner < 2; ++owner)
1012  {
1013  const bool same_player = (owner == 0);
1014  for (int y1 = 0; y1 < 10; ++y1)
1015  {
1016  for (int y2 = 0; y2 < 10; ++y2)
1017  {
1018  for (int promoted1 = 0; promoted1 < 2; ++promoted1)
1019  {
1020  for (int promoted2 = 0; promoted2 < 2; ++promoted2)
1021  {
1022  if (same_player)
1023  {
1024  int y1p = y1;
1025  int y2p = y2;
1026  int promoted1p = promoted1;
1027  int promoted2p = promoted2;
1028  if (y1 > y2 || (y1 == y2 && !promoted1 && promoted2))
1029  {
1030  std::swap(y1p, y2p);
1031  std::swap(promoted1p, promoted2p);
1032  }
1033  table[index(same_player, promoted1, promoted2,
1034  y1, y2)] =
1035  orig_table[index(same_player, promoted1p, promoted2p,
1036  y1p, y2p)];
1037  }
1038  else
1039  {
1040  if (y1 + y2 > 10 || y1 == 0 ||
1041  (y1 + y2 == 10 && promoted1))
1042  {
1043  const int idx = index(same_player, promoted1, promoted2,
1044  y1, y2);
1045  table[idx] = orig_table[idx];
1046  }
1047  else
1048  {
1049  table[index(same_player, promoted1, promoted2,
1050  y1, y2)] =
1051  -orig_table[index(same_player, promoted2, promoted1,
1052  (10 - y2) % 10, (10 - y1) % 10)];
1053  }
1054  }
1055  }
1056  }
1057  }
1058  }
1059  }
1060 }
1061 
1063 RookRook::eval(const NumEffectState &state)
1064 {
1065  MultiInt result;
1066  Piece rook1 = state.pieceOf(PtypeTraits<ROOK>::indexMin);
1067  Piece rook2 = state.pieceOf(PtypeTraits<ROOK>::indexMin + 1);
1068  if (rook1.owner() == rook2.owner())
1069  {
1070  if (rook1.owner() == BLACK)
1071  {
1072  result += table[index<true, BLACK>(rook1, rook2)];
1073  }
1074  else
1075  {
1076  result -= table[index<true, WHITE>(rook1, rook2)];
1077  }
1078  }
1079  else
1080  {
1081  if (rook1.owner() != BLACK)
1082  {
1083  std::swap(rook1, rook2);
1084  }
1085  result += table[index<false, BLACK>(rook1, rook2)];
1086  }
1087  return result;
1088 }
1089 
1090 
1093 
1094 void osl::eval::ml::
1096 {
1097  for (size_t i = 0; i < ONE_DIM; ++i)
1098  {
1099  for (int s=0; s<NStages; ++s)
1100  table[i][s] = weights.value(i + ONE_DIM*s);
1101  }
1102 }
1103 
1105 RookRookPiece::eval(const NumEffectState &state)
1106 {
1107  MultiInt result;
1108  const Piece rook1 = state.pieceOf(PtypeTraits<ROOK>::indexMin);
1109  const Piece rook2 = state.pieceOf(PtypeTraits<ROOK>::indexMin + 1);
1110  if (!rook1.isOnBoard() || !rook2.isOnBoard() ||
1111  rook1.owner() == rook2.owner())
1112  return result;
1113 
1114  if (state.hasEffectByPtype<ROOK>(rook2.owner(), rook1.square()))
1115  return result;
1116 
1117  Direction dir;
1118  bool vertical = false;
1119  if (rook1.square().x() == rook2.square().x())
1120  {
1121  vertical = true;
1122  if (rook1.square().y() < rook2.square().y())
1123  {
1124  dir = D;
1125  }
1126  else
1127  {
1128  dir = U;
1129  }
1130  }
1131  else if (rook1.square().y() == rook2.square().y())
1132  {
1133  if (rook1.square().x() < rook2.square().x())
1134  {
1135  dir = L;
1136  }
1137  else
1138  {
1139  dir = R;
1140  }
1141  }
1142  else
1143  {
1144  return result;
1145  }
1146 
1147  Square p1 = state.mobilityOf(dir, rook1.number());
1148  Square p2 = state.mobilityOf(inverse(dir), rook2.number());
1149  assert(p1.isOnBoard() && p2.isOnBoard());
1150  if (p1 == p2)
1151  {
1152  const Piece p = state.pieceAt(p1);
1153  const bool black_with_support =
1154  state.hasEffectAt<BLACK>(rook1.owner() == BLACK ?
1155  rook1.square() : rook2.square());
1156  const bool white_with_support =
1157  state.hasEffectAt<WHITE>(rook1.owner() == WHITE ?
1158  rook1.square() : rook2.square());
1159  if (p.owner() == BLACK)
1160  {
1161  result += table[index(p.ptype(), black_with_support,
1162  white_with_support, vertical)];
1163  }
1164  else
1165  {
1166  result -= table[index(p.ptype(), white_with_support,
1167  black_with_support, vertical)];
1168  }
1169  }
1170  return result;
1171 }
1172 
1173 
1176 
1177 void osl::eval::ml::
1179 {
1180  for (size_t i = 0; i < ONE_DIM; ++i)
1181  {
1182  for (int s=0; s<NStages; ++s)
1183  table[i][s] = weights.value(i + ONE_DIM*s);
1184  }
1185 }
1186 
1188 BishopStandFile5::eval(const NumEffectState &state)
1189 {
1190  MultiInt result;
1191  if (state.hasPieceOnStand<BISHOP>(BLACK))
1192  {
1193  result += table[ptypeOIndex(state.pieceAt(Square(5, 3)).ptypeO())];
1194  }
1195  if (state.hasPieceOnStand<BISHOP>(WHITE))
1196  {
1197  PtypeO ptypeO = state.pieceAt(Square(5, 7)).ptypeO();
1198  ptypeO = altIfPiece(ptypeO);
1199  result -= table[ptypeOIndex(ptypeO)];
1200  }
1201  return result;
1202 }
1203 
1204 
1205 
1208 
1209 void osl::eval::ml::
1211 {
1212  for (size_t i = 0; i < ONE_DIM; ++i)
1213  {
1214  for (int s=0; s<NStages; ++s)
1215  table[i][s] = weights.value(i + ONE_DIM*s);
1216  }
1217 }
1218 
1219 template <osl::Player Owner>
1221 MajorCheckWithCapture::addOne(const NumEffectState &state)
1222 {
1223  const Square king = state.kingSquare(Owner);
1224  PieceMask pieces = state.effectedMask(alt(Owner));
1225  pieces &= state.piecesOnBoard(Owner);
1226  pieces &= ~state.effectedMask(Owner);
1227  MultiInt sum;
1228  while (pieces.any()) {
1229  const Piece p = state.pieceOf(pieces.takeOneBit());
1230  const Square sq = p.square();
1231  if (state.hasLongEffectAt<ROOK>(alt(Owner), sq)
1232  && state.hasEffectIf(newPtypeO(BLACK,ROOK), sq, king)) {
1233  if (Owner == BLACK)
1234  sum += table[index(p.ptype(), true, sq.canPromote(alt(Owner)))];
1235  else
1236  sum -= table[index(p.ptype(), true, sq.canPromote(alt(Owner)))];
1237  }
1238  if (state.hasLongEffectAt<BISHOP>(alt(Owner), sq)
1239  && state.hasEffectIf(newPtypeO(BLACK,BISHOP), sq, king)) {
1240  if (Owner == BLACK)
1241  sum += table[index(p.ptype(), false, sq.canPromote(alt(Owner)))];
1242  else
1243  sum -= table[index(p.ptype(), false, sq.canPromote(alt(Owner)))];
1244  }
1245  }
1246  return sum;
1247 }
1248 
1250 MajorCheckWithCapture::eval(const NumEffectState &state)
1251 {
1252  return addOne<BLACK>(state) + addOne<WHITE>(state);
1253 }
1254 
1255 
1258 
1259 void osl::eval::ml::
1261 {
1262  for (size_t i = 0; i < ONE_DIM; ++i)
1263  {
1264  for (int s=0; s<NStages; ++s)
1265  table[i][s] = weights.value(i + ONE_DIM*s);
1266  }
1267 }
1268 
1270 RookSilverKnight::eval(const NumEffectState &state)
1271 {
1272  MultiInt result;
1273  for (int i = PtypeTraits<ROOK>::indexMin;
1274  i < PtypeTraits<ROOK>::indexLimit;
1275  ++i)
1276  {
1277  const Piece rook = state.pieceOf(i);
1278  if (!rook.isOnBoard())
1279  {
1280  continue;
1281  }
1282  for (int i = PtypeTraits<SILVER>::indexMin;
1283  i < PtypeTraits<SILVER>::indexLimit;
1284  ++i)
1285  {
1286  const Piece silver = state.pieceOf(i);
1287  if (!silver.isOnBoard() || silver.isPromoted() ||
1288  silver.owner() != rook.owner())
1289  {
1290  continue;
1291  }
1292  for (int i = PtypeTraits<KNIGHT>::indexMin;
1293  i < PtypeTraits<KNIGHT>::indexLimit;
1294  ++i)
1295  {
1296  const Piece knight = state.pieceOf(i);
1297  if (!knight.isOnBoard() || knight.isPromoted() ||
1298  knight.owner() != rook.owner())
1299  {
1300  continue;
1301  }
1302 
1303  if (rook.owner() == BLACK)
1304  {
1305  if (rook.square().x() > 5)
1306  {
1307  result += table[index(9 - rook.square().x(), rook.square().y() - 1,
1308  9 - silver.square().x(), silver.square().y() - 1,
1309  9 - knight.square().x(), knight.square().y() - 1)];
1310  }
1311  else
1312  {
1313  result += table[index(rook.square().x() - 1, rook.square().y() - 1,
1314  silver.square().x() - 1, silver.square().y() - 1,
1315  knight.square().x() - 1, knight.square().y() - 1)];
1316  }
1317  }
1318  else
1319  {
1320  if (rook.square().x() >= 5)
1321  {
1322  result -= table[index(9 - rook.square().x(), 9 - rook.square().y(),
1323  9 - silver.square().x(), 9 - silver.square().y(),
1324  9 - knight.square().x(), 9 - knight.square().y())];
1325  }
1326  else
1327  {
1328  result -= table[index(rook.square().x() - 1, 9 - rook.square().y(),
1329  silver.square().x() - 1, 9 - silver.square().y(),
1330  knight.square().x() - 1, 9 - knight.square().y())];
1331  }
1332  }
1333  }
1334  }
1335  }
1336  return result;
1337 }
1338 
1339 
1342 
1343 void osl::eval::ml::
1345 {
1346  for (size_t i = 0; i < ONE_DIM; ++i)
1347  {
1348  for (int s=0; s<NStages; ++s)
1349  table[i][s] = weights.value(i + ONE_DIM*s);
1350  }
1351 }
1352 
1354 BishopSilverKnight::eval(const NumEffectState &state)
1355 {
1356  MultiInt result;
1357  for (int i = PtypeTraits<BISHOP>::indexMin;
1358  i < PtypeTraits<BISHOP>::indexLimit;
1359  ++i)
1360  {
1361  const Piece bishop = state.pieceOf(i);
1362  if (!bishop.isOnBoard())
1363  {
1364  continue;
1365  }
1366  for (int i = PtypeTraits<SILVER>::indexMin;
1367  i < PtypeTraits<SILVER>::indexLimit;
1368  ++i)
1369  {
1370  const Piece silver = state.pieceOf(i);
1371  if (!silver.isOnBoard() || silver.isPromoted() ||
1372  silver.owner() != bishop.owner())
1373  {
1374  continue;
1375  }
1376  for (int i = PtypeTraits<KNIGHT>::indexMin;
1377  i < PtypeTraits<KNIGHT>::indexLimit;
1378  ++i)
1379  {
1380  const Piece knight = state.pieceOf(i);
1381  if (!knight.isOnBoard() || knight.isPromoted() ||
1382  knight.owner() != bishop.owner())
1383  {
1384  continue;
1385  }
1386 
1387  if (bishop.owner() == BLACK)
1388  {
1389  if (bishop.square().x() > 5)
1390  {
1391  result += table[index(9 - bishop.square().x(), bishop.square().y() - 1,
1392  9 - silver.square().x(), silver.square().y() - 1,
1393  9 - knight.square().x(), knight.square().y() - 1)];
1394  }
1395  else
1396  {
1397  result += table[index(bishop.square().x() - 1, bishop.square().y() - 1,
1398  silver.square().x() - 1, silver.square().y() - 1,
1399  knight.square().x() - 1, knight.square().y() - 1)];
1400  }
1401  }
1402  else
1403  {
1404  if (bishop.square().x() >= 5)
1405  {
1406  result -= table[index(9 - bishop.square().x(), 9 - bishop.square().y(),
1407  9 - silver.square().x(), 9 - silver.square().y(),
1408  9 - knight.square().x(), 9 - knight.square().y())];
1409  }
1410  else
1411  {
1412  result -= table[index(bishop.square().x() - 1, 9 - bishop.square().y(),
1413  silver.square().x() - 1, 9 - silver.square().y(),
1414  knight.square().x() - 1, 9 - knight.square().y())];
1415  }
1416  }
1417  }
1418  }
1419  }
1420  return result;
1421 }
1422 
1423 
1426 
1427 void osl::eval::ml::
1429 {
1430  for (size_t i = 0; i < ONE_DIM; ++i) {
1431  for (int s=0; s<NStages; ++s)
1432  table[i][s] = weights.value(i + ONE_DIM*s);
1433  if (i > 0)
1434  table[i] += table[0];
1435  }
1436 }
1437 
1438 template <osl::Player P>
1439 void osl::eval::ml::
1440 AttackMajorsInBase::addOne(const NumEffectState &state, Piece rook, MultiInt& result)
1441 {
1442  Square sq = rook.square();
1443  if (state.hasEffectAt(alt(P), sq)
1444  || sq.squareForBlack(P).y() < 8)
1445  return;
1446  typedef std::pair<Offset,Square> pair_t;
1447  const CArray<pair_t, 7> bishop_attack =
1448  {{
1449  pair_t(Offset::make<P,U>(), sq.neighbor<P, UL>()),
1450  pair_t(Offset::make<P,U>(), sq.neighbor<P, UR>()),
1451  pair_t(Offset::make<P,L>(), sq.neighbor<P, UL>()),
1452  pair_t(Offset::make<P,R>(), sq.neighbor<P, UR>()),
1453  pair_t(Offset::make<P,D>(), sq.neighbor<P, UL>()),
1454  pair_t(Offset::make<P,D>(), sq.neighbor<P, UR>()),
1455  pair_t(Offset::make<P,U>(), sq.neighbor<P, U>()),
1456  }};
1457  const bool has_gold = state.hasPieceOnStand(alt(P), GOLD);
1458  const bool rook_support = state.hasEffectAt(P, sq);
1459  BOOST_FOREACH(pair_t pair, bishop_attack) {
1460  const Square attack_square = pair.second;
1461  if (! state[attack_square].isEmpty()
1462  || state.countEffect(P, attack_square) > 1)
1463  continue;
1464  const Square bishop_square = attack_square + pair.first;
1465  Piece p = state[bishop_square];
1466  if (! p.isPlayerPtype(P,BISHOP)
1467  || state.hasEffectAt(alt(P), bishop_square))
1468  continue;
1469  int a = state.countEffect(alt(P), attack_square) + has_gold;
1470  if (a <= state.countEffect(P, attack_square))
1471  continue;
1472  const int i = index(state.findCheapAttack(P, attack_square).ptype(),
1473  state.findCheapAttack(alt(P), attack_square).ptype(),
1474  has_gold, rook_support,
1475  state.hasEffectNotBy(P, rook, bishop_square));
1476  if (P == BLACK)
1477  result += table[i];
1478  else
1479  result -= table[i];
1480  }
1481 }
1482 
1484 AttackMajorsInBase::eval(const NumEffectState &state)
1485 {
1486  MultiInt result;
1487  for (int i=0; i<state.nthLimit<ROOK>(); ++i) {
1488  const Piece rook = state.nth<ROOK>(i);
1489  if (! rook.isOnBoard() || rook.isPromoted())
1490  continue;
1491  Player P = rook.owner();
1492  if (P == BLACK)
1493  addOne<BLACK>(state, rook, result);
1494  else
1495  addOne<WHITE>(state, rook, result);
1496  }
1497  return result;
1498 }
1499 
1500 
1501 namespace osl
1502 {
1503  namespace eval
1504  {
1505  namespace ml
1506  {
1507  template class MajorY<true, ROOK>;
1508  template class MajorY<false, ROOK>;
1509  template class MajorY<true, BISHOP>;
1510  template class MajorY<false, BISHOP>;
1511  template class RookPawn<true>;
1512  template class RookPawn<false>;
1513  template class MajorGoldSilverAttacked<false>;
1514  template MultiInt KingRookBishop::evalOne<BLACK>(const NumEffectState &state);
1515  template MultiInt KingRookBishop::evalOne<WHITE>(const NumEffectState &state);
1516  }
1517  }
1518 }
1519 
1520 // ;;; Local Variables:
1521 // ;;; mode:c++
1522 // ;;; c-basic-offset:2
1523 // ;;; End: