public static StringBuilder AppendCastleRights( this StringBuilder sb, HiFlags fBlackHi, HiFlags fWhiteHi, CastleRule castle) { if (((fBlackHi | fWhiteHi) & HiFlags.CanCastleMask) == 0) { sb.Append("-"); } else if (castle is not null && castle.IsChess960) { var ruleWhite = castle.RuleParameter[White]; if ((fWhiteHi & HiFlags.CanOO) != 0 && ruleWhite.RookOOFrom.HasValue) { sb.Append((Char)('A' + ruleWhite.RookOOFrom)); } if ((fWhiteHi & HiFlags.CanOOO) != 0 && ruleWhite.RookOOOFrom.HasValue) { sb.Append((Char)('A' + ruleWhite.RookOOOFrom)); } var ruleBlack = castle.RuleParameter[Black]; if ((fBlackHi & HiFlags.CanOO) != 0 && ruleBlack.RookOOFrom.HasValue) { sb.Append((Char)('a' + ruleBlack.RookOOFrom - nRankLast)); } if ((fBlackHi & HiFlags.CanOOO) != 0 && ruleBlack.RookOOOFrom.HasValue) { sb.Append((Char)('a' + ruleBlack.RookOOOFrom - nRankLast)); } }
// Recycle Compositions to reduce garbage: public void Recycle(CompositionCounter wPieceCounts, HiFlags fhi) { PieceCounts = wPieceCounts; FlagsCV = CVFlags.IsValid; FlagsHi = fhi; weighPieces(out Value, wPieceCounts, fhi); }
protected static Boolean sameBishops(HiFlags fBlackHi, HiFlags fWhiteHi) { var blackPair = fBlackHi & HiFlags.Pair; var whitePair = fWhiteHi & HiFlags.Pair; return((whitePair == HiFlags.Lite && blackPair == HiFlags.Lite) || (whitePair == HiFlags.Dark && blackPair == HiFlags.Dark)); }
// // To be considered "Wrong" a given side must have a Bishop to begin with. // Wrong Bishops DO NOT protect the queening square of a Passed Rook Pawn: // private static Boolean punishWrongBishop(PRPFlags fprp, HiFlags fhi) { var bWrong = ((fhi & HiFlags.Pair) != 0) && ((fprp & PRPFlags.Both) != 0) && ((((fprp & PRPFlags.Lite) != 0) && (fhi & HiFlags.Lite) == 0) || (((fprp & PRPFlags.Dark) != 0) && (fhi & HiFlags.Dark) == 0)); return(bWrong); }
// Recycle Compositions to reduce garbage: public void Recycle(CompositionCounter wBlackCounts, CompositionCounter wWhiteCounts, HiFlags fBlackHi, HiFlags fWhiteHi) { //HashPiece = qHashPiece; BlackCounts = wBlackCounts; WhiteCounts = wWhiteCounts; FlagsCV = CVFlags.IsValid; FlagsBlackHi = fBlackHi; FlagsWhiteHi = fWhiteHi; weighPieces(out Delta, out Total, wBlackCounts, wWhiteCounts, fBlackHi, fWhiteHi); }
// Used in the Composition2 Constructor internal static void weighPieces(out Eval Value, CompositionCounter wPieceCounts, HiFlags fhi) { var nSum = 0; for (var vPiece = vCompositionOffset; vPiece < vK6; vPiece++, wPieceCounts >>= nPerNibble) { nSum += nibble(wPieceCounts) * PieceWeight[vPiece]; } #if EvalBishopPair //[Old]15 MHz with 20 MHz without if (bishopPair(fhi)) { nSum += mBishopPairWeight; } #endif Value = (Eval)nSum; }
// Used in the Composition Constructor internal static void weighPieces(out Eval Delta, out Eval Total, CompositionCounter wBlackCounts, CompositionCounter wWhiteCounts, HiFlags fBlackHi, HiFlags fWhiteHi) { var nSumDelta = 0; var nSumTotal = 0; for (var vPiece = vCompositionOffset; vPiece < vK6; vPiece++, wBlackCounts >>= nPerNibble, wWhiteCounts >>= nPerNibble) { var nBlack = nibble(wBlackCounts); var nWhite = nibble(wWhiteCounts); var nDelta = nWhite - nBlack; var nTotal = nWhite + nBlack; nSumDelta += nDelta * PieceWeight[vPiece]; nSumTotal += nTotal * PieceWeight[vPiece]; } #if EvalBishopPair //[Old]15 MHz with 20 MHz without if (bishopPair(fBlackHi)) { nSumDelta -= mBishopPairWeight; nSumTotal += mBishopPairWeight; } if (bishopPair(fWhiteHi)) { nSumDelta += mBishopPairWeight; nSumTotal += mBishopPairWeight; } #endif Delta = (Eval)nSumDelta; Total = (Eval)nSumTotal; }
public static String FormatFlags( ModeFlags fmd, DrawFlags fdr, EGFlags feg, HiFlags fBlackHi, HiFlags fWhiteHi, LoFlags flo) { if (fmd == 0 && fdr == 0 && feg == 0 && fBlackHi == 0 && fWhiteHi == 0 && flo == 0) { return("None"); } var sBlackHi = FormatFlags(fBlackHi); var sWhiteHi = FormatFlags(fWhiteHi); var sBlackHiLabelled = IsNullOrEmpty(sBlackHi) ? Empty : $"Black[{sBlackHi}]"; var sWhiteHiLabelled = IsNullOrEmpty(sWhiteHi) ? Empty : $"White[{sWhiteHi}]"; const Int32 nCapacity = 4; var sFlags = new List <String>(nCapacity) .AddNotEmpty(FormatFlags(fmd)) .AddNotEmpty(FormatFlags(fdr)) .AddNotEmpty(FormatFlags(feg)) .AddNotEmpty(sBlackHiLabelled) .AddNotEmpty(sWhiteHiLabelled) .AddNotEmpty(FormatFlags(flo)); return(Join(sSpace, sFlags)); }
// // The MaterialBalance Conditional makes a simplifying assumption that // material value can be assessed independently for the two sides. // // However, research has shown that material evaluation depends on which // pieces the are possessed by the two sides. There are conquest cycles: // A Bishop Pair is more effective against an opposing Rook, for example. // // See "The Evaluation of Material Imbalances" by IM Larry Kaufman // https://www.chess.com/article/view/the-evaluation-of-material-imbalances-by-im-larry-kaufman // #if MaterialBalance public Composition2 GetCX2(Position position, PieceHashcode wMemoHash, CompositionCounter wPieceCounts, HiFlags fhi) { CXPMemo.Counts.GetReads++; var found = CXPMemo[wMemoHash]; fhi &= HiFlags.Pair; //[Note]Only HiFlags.Pair are cached for use by weighPieces() var fhiFound = found.FlagsHi & HiFlags.Pair; #if CompositionByValue var bDefault = (found.FlagsCV & Composition2.CVFlags.IsValid) == 0; #else var bDefault = found == default(PawnPosition); #endif if (!bDefault && found.PieceCounts == wPieceCounts && fhi == fhiFound) { CXPMemo.Counts.GetHits++; // Match, a.k.a. Get Hit return(found); } #if CompositionByValue if (bDefault) { CXPMemo.Counts.Added++; // Non-Match Case: Add new Composition } #if DebugHashPieces else { var sb = new StringBuilder(); //DisplayCurrent("GetCX2()"); sb.AppendLine(); sb.Append("Old "); sb.AppendPieceCounts(White, wPieceCounts); sb.AppendLine(); sb.Append("New "); sb.AppendPieceCounts(White, found.PieceCounts); sb.AppendLine(); sb.AppendFormat($"Index = {CXPMemo.index(wMemoHash)}"); sb.AppendLine(); sb.FlushLine(); } #endif found = new Composition2(wPieceCounts, fhi); CXPMemo[wMemoHash] = found; return(found); #else // CompositionByValue if (bDefault) { CXPMemo.Counts.Added++; // Non-Match Case: Add new Composition found = new Composition2(wPieceCounts, fBlackHi, fWhiteHi); CXPMemo[wMemoHash] = found; return(found); } else { found.Recycle(wPieceCounts, fBlackHi, fWhiteHi); return(found); } #endif }
public Composition GetCXP(Position position, MemoHashcode uMemoHash, CompositionCounter wBlackCounts, CompositionCounter wWhiteCounts, HiFlags fBlackHi, HiFlags fWhiteHi) { CXPMemo.Counts.GetReads++; var found = CXPMemo[uMemoHash]; fBlackHi &= HiFlags.Pair; //[Note]Only HiFlags.Pair are cached for use by weighPieces() fWhiteHi &= HiFlags.Pair; #if CompositionByValue var bDefault = (found.FlagsCV & Composition.CVFlags.IsValid) == 0; #else var bDefault = found == default(Composition); #endif if (!bDefault) { var fBlackHiFound = found.FlagsBlackHi & HiFlags.Pair; var fWhiteHiFound = found.FlagsWhiteHi & HiFlags.Pair; if (found.BlackCounts == wBlackCounts && found.WhiteCounts == wWhiteCounts && fBlackHi == fBlackHiFound && fWhiteHi == fWhiteHiFound) { CXPMemo.Counts.GetHits++; // Match, a.k.a. Get Hit return(found); } } #if CompositionByValue if (bDefault) { CXPMemo.Counts.Added++; // Non-Match Case: Add new Composition } #if DebugHashPieces else { var sb = new StringBuilder(); //DisplayCurrent("GetCXP()"); sb.AppendLine(); sb.Append("Old "); sb.AppendPieceCounts(Side[Black], Side[White]); sb.AppendLine(); sb.Append("New "); sb.AppendPieceCounts(found.Side[Black], found.Side[White]); sb.AppendLine(); sb.AppendFormat($"Index = {memo.index(uMemoHash)}"); sb.AppendLine(); sb.FlushLine(); } #endif found = new Composition(wBlackCounts, wWhiteCounts, fBlackHi, fWhiteHi); CXPMemo[uMemoHash] = found; return(found); #else // CompositionByValue if (bDefault) { CXPMemo.Counts.Added++; // Non-Match Case: Add new Composition found = new Composition(wBlackCounts, wWhiteCounts, fBlackHi, fWhiteHi); CXPMemo[uMemoHash] = found; return(found); } else { found.Recycle(wBlackCounts, wWhiteCounts, fBlackHi, fWhiteHi); return(found); } #endif }
protected static Boolean bishopPair(HiFlags fhi) { return((fhi & HiFlags.Pair) == HiFlags.Pair); }
public static String FormatFlags(HiFlags fhi) { var en = hiFlags.Where(f => (f & fhi) != 0); return(Join(sSpace, en)); }