private async static Task <Solution> Pack_async(PartList parts, BoardList stock) { List <Task> threads = new List <Task>(); int stockcount = stock.Count; Solution[] solutions = new Solution[stockcount]; for (int i = 0; i < stockcount; i++) { threads.Add( Task.Factory.StartNew(async(o) => { int ii = (int)o; Item iStock = stock[ii]; PartList mycopyofParts = parts.Copy(); Part iPart = mycopyofParts[0]; mycopyofParts.RemoveAt(0); if (!iStock.TrySplit(iPart, out Item H1, out Item H2, out Item V1, out Item V2)) { return; } if (mycopyofParts.Count == 0) { solutions[ii] = new Solution(iPart, iStock); return; } BoardList myVstock = stock.Copy(); myVstock.Remove(iStock); myVstock.AddRange(V2, V1); Solution solV = PackALL(mycopyofParts, myVstock); if (solV != null) { solutions[ii] = new Solution(iPart, iStock); solutions[ii].AddRange(solV); return; } BoardList myHstock = stock.Copy(); myHstock.Remove(iStock); myHstock.AddRange(H2, H1); Solution solH = PackALL(mycopyofParts, myHstock); if (solH != null) { solutions[ii] = new Solution(iPart, iStock); solutions[ii].AddRange(solH); return; } }, i)); } Task.WaitAll(threads.ToArray()); return(solutions.FirstOrDefault(t => t != null)); }
/// <summary> /// ALL parts must fit for an acceptable solution - we use this to check if a given combination of parts will fit on a board. /// </summary> /// <param name="parts"></param> /// <param name="stock"></param> /// <returns></returns> private static Solution PackALL(PartList parts, BoardList stock) { Solution sol = new Solution(); PartList mycopyofParts = parts.Copy(); Part iPart = mycopyofParts[0]; mycopyofParts.RemoveAt(0); int stockcount = stock.Count; for (int i = 0; i < stockcount; i++) { Item iStock = stock[i]; if (!iStock.TrySplit(iPart, out Item H1, out Item H2, out Item V1, out Item V2)) { continue; } if (mycopyofParts.Count == 0) { sol.Add(iPart, iStock); return(sol); } BoardList myVstock = stock.Copy(); myVstock.Remove(iStock); myVstock.AddRange(V2, V1); Solution solV = PackALL(mycopyofParts, myVstock); if (solV != null) { sol.Add(iPart, iStock); sol.AddRange(solV); return(sol); } BoardList myHstock = stock.Copy(); myHstock.Remove(iStock); myHstock.AddRange(H2, H1); Solution solH = PackALL(mycopyofParts, myHstock); if (solH != null) { sol.Add(iPart, iStock); sol.AddRange(solH); return(sol); } } return(null); }