public bool NiceLoop( ) //Depth-first Search { Prepare(); CeLKMan.PrepareCellLink(1 + 2); //Generate StrongLink,WeakLink for (int szCtrl = 4; szCtrl < NiceLoopMax; szCtrl++) { foreach (var P0 in pBDL.Where(p => (p.No == 0))) //Origin Cell { foreach (var no in P0.FreeB.IEGet_BtoNo()) //Origin Number { foreach (var LKH in CeLKMan.IEGetRcNoType(P0.rc, no, 3)) //First Link { if (pAnMan.CheckTimeOut()) { return(false); } var SolStack = new Stack <UCellLink>(); SolStack.Push(LKH); Bit81 UsedCells = new Bit81(LKH.rc2); //Bit Representation of Used Cells _NL_Search(LKH, LKH, SolStack, UsedCells, szCtrl - 1); if (SolCode > 0) { return(true); } } } } } return(false); }
private IEnumerable <Bit81[]> _GetXYChain(List <int> LKRec) { List <UCell> TBDbv = pBDL.FindAll(p => (p.FreeBC == 2)); //Extract BV_Cell(BV:bivalue). foreach (var PS in TBDbv) //Choose one BV_Cell(=>PS) { int rcS = PS.rc; foreach (var no in PS.FreeB.IEGet_BtoNo()) //Choose one digit(in PS) { int noB = (1 << no); Bit81[] CRL = new Bit81[2]; CRL[0] = new Bit81(); //Position of the target digit to be concatenated CRL[1] = new Bit81(); //Position of other digits to be connected CRL[0].ID = rcS; CRL[1].ID = no; Bit81 CnctdCs = ConnectedCells[rcS]; //Associated cells group of starting cell Queue <int> rcQue = new Queue <int>(); int no0 = pBDL[rcS].FreeB.BitReset(no).BitToNum(); //The other digit of the starting cell rcQue.Enqueue((no0 << 8) | rcS); LKRec.Clear(); while (rcQue.Count > 0) //Extend the chain step by step { int rcX = rcQue.Dequeue(); int no1 = rcX >> 8, rc1 = rcX & 0xFF; foreach (var LK in CeLKMan.IEGetRcNoType(rc1, no1, 1)) //strongLink connected with rc1, #no { int rc2 = LK.rc2; if (pBDL[rc2].FreeBC != 2) { continue; //bivalue? } if (CRL[0].IsHit(rc2) || CRL[1].IsHit(rc2)) { continue; //Different from colored cells? } //Exclude cells associated with the starting cell and having the same digit if (CnctdCs.IsHit(rc2) && (pBDL[rc2].FreeB & noB) > 0) { continue; } int no2 = (pBDL[rc2].FreeB.BitReset(no1)).BitToNum(); //other digit int nx = (no2 == no)? 0: 1; CRL[nx].BPSet(rc2); rcQue.Enqueue((no2 << 8) | rc2); //Put the next [Digit&Cell] in Queue LKRec.Add((rc1 << 8 | rc2)); //Record Link } } if (CRL[0].Count > 0 || CRL[1].Count > 0) { yield return(CRL); } } } yield break; }
private IEnumerable <Bit81[]> _GetXChain(int no, List <int> LKRec) { Bit81 TBD = new Bit81(pBDL, (1 << no)); int rcS; while ((rcS = TBD.FindFirstrc()) >= 0) //rcS:Set the origin cell. { TBD.BPReset(rcS); //Reset TBD to Processed. //===== Repeatedly coloring processing. initialize ===== Bit81[] CRL = new Bit81[3]; //Coloring 2 groups(CRL[0] and CRL[1]). CRL[0] = new Bit81(); CRL[1] = new Bit81(rcS); CRL[2] = new Bit81(); CRL[0].ID = rcS; Queue <int> rcQue = new Queue <int>(); rcQue.Enqueue((rcS << 1) | 1); //(First StrongLink) //===== Repeatedly coloring processing. start ===== LKRec.Clear(); //clear chain recorder. bool firstLK = true; while (rcQue.Count > 0) { int rcX = rcQue.Dequeue(); //recorded [cell and color] int swF = 1 - (rcX & 1); //next color(inversion S-W) int rc1 = (rcX >> 1); //next cell foreach (var LKx in CeLKMan.IEGetRcNoType(rc1, no, (swF + 1))) //LKx:link connected to cell rc1 { int rc2 = LKx.rc2; //anather cell of LKx if ((CRL[0] | CRL[1]).IsHit(rc2)) { continue; //already colored } CRL[swF].BPSet(rc2); //coloring rcQue.Enqueue((rc2 << 1) | swF); //enqueue(next cell and color) LKRec.Add(rc1 << 8 | rc2); //chain record if (firstLK) { CRL[2].BPSet(rc2); //record colored cells from rcS(source cell) } } firstLK = false; } if (CRL[1].Count > 0) { yield return(CRL); } //----- Repeatedly coloring processing. end ----- } yield break; }
private IEnumerable <Bit81[]> _Coloring(int no) { Bit81[] CRL = new Bit81[2]; CRL[0] = new Bit81(); CRL[1] = new Bit81(); Bit81 TBD = new Bit81(pBDL, (1 << no)); int rc1 = TBD.FindFirstrc(); while (rc1 >= 0) { Queue <int> rcQue = new Queue <int>(); rcQue.Enqueue(rc1 << 1); CRL[0].BPSet(rc1); TBD.BPReset(rc1); while (rcQue.Count > 0) { rc1 = rcQue.Dequeue(); int kx = 1 - (rc1 & 1); rc1 >>= 1; TBD.BPReset(rc1); foreach (var P in CeLKMan.IEGetRcNoType(rc1, no, 1)) { int rc2 = P.rc2; if (!(CRL[0] | CRL[1]).IsHit(rc2) && TBD.IsHit(rc2)) { CRL[kx].BPSet(rc2); rcQue.Enqueue((rc2 << 1) | kx); } } } yield return(CRL); if ((rc1 = TBD.FindFirstrc()) < 0) { yield break; } CRL = new Bit81[2]; CRL[0] = new Bit81(); CRL[1] = new Bit81(); } yield break; }