//Given a MyMatrAdj, this function creates a list of paths of length >=3 (line or circumference). //Exception: when it finds a path of length n or n-1 (n = number of centroids on the current MyGroupingSurface) //. the function early recalls the geometric check of MyRepeatedEntities corresponding to the centroids. // INPUT: a MyMatrAdj and a list of MyRepeatedEntity (on a MyGroupingSurface) // OUTPUT: it returns TRUE if it finds a pattern of length = n or length = n -1, FALSE otherwise // it returns a list of detected MyPathOfPoints (still to verify the geometry) // a bool onlyShortPaths which is TRUE if there are not paths of length > 2, FALSE otherwise // it updates the lists of final pattern (already geometrically verified), the list of MyMatrAdj // of the current MyGroupingSurface, the list of MyGroupingSurface. //There is also a Tolerance check: if it is not satisfied it stops the procedure. //This function classifies the points involved in a given MyMatrAdj, subdividing them in the respective list public static void ClassifyComponents(MyMatrAdj matrAdjToSee, int n, ref List <int> listOfExtremePoints, ref List <int> listOfSimplePoints, ref List <int> listOfMBPoints) { for (var i = 0; i < n; i++) { var tot = 0; for (var j = 0; j < n; j++) { tot += matrAdjToSee.matr[i, j]; } if (tot == 1) { listOfExtremePoints.Add(i); } if (tot == 2) { listOfSimplePoints.Add(i); } if (tot > 2) { listOfMBPoints.Add(i); } } }
//This function returns the list of paths obtained given the Start point. public static void OnePointGivenPaths_ComposedPatterns(MyMatrAdj matrAdjToSee, int n, int startPointInd, List <MyPattern> listOfParallelPatterns, List <MyVertex> listCentroid, List <int> listOfExtremePoints, ref List <int> listOfSimplePoints_Copy, List <int> listOfMBPoints, ref bool longestPattern, ref List <MyPathOfPoints> listOfPaths, ref List <int> listOfPenultimate, ref List <int> listOfLast, ref StringBuilder fileOutput, ref bool toleranceOk, ref List <MyMatrAdj> listOfMatrAdj, ref List <MyGroupingSurfaceForPatterns> listOfMyGroupingSurface, ref List <MyComposedPattern> listOfOutputComposedPattern, ref List <MyComposedPattern> listOfOutputComposedPatternTwo, ref List <int> listOfIndicesOfLongestPath, SldWorks SwApplication) { List <int> BranchesFirst = matrAdjToSee.matr.GetRow(startPointInd).Find(entry => entry == 1).ToList(); //List<int> BranchesFirst = nInd.FindAll(ind => MatrAdjToSee.matr[StartPointInd, ind] == 1); foreach (int branch1 in BranchesFirst) { fileOutput.AppendLine("\n branch di StartPoint " + startPointInd + ": " + branch1); TwoPointsGivenPaths_ComposedPatterns(matrAdjToSee, n, startPointInd, branch1, listOfParallelPatterns, listCentroid, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfMyGroupingSurface, ref listOfOutputComposedPattern, ref listOfOutputComposedPatternTwo, ref listOfIndicesOfLongestPath, SwApplication); if (toleranceOk == false || longestPattern) { return; } } }
//This function returns the list of paths obtained given the Start point. public static void OnePointGivenPaths_Assembly_ComposedPatterns(MyMatrAdj matrAdjToSee, int n, int startPointInd, List <MyPatternOfComponents> listOfPatternsOfComponents, List <MyVertex> listOfCentroids, List <int> listOfExtremePoints, ref List <int> listOfSimplePoints_Copy, List <int> listOfMBPoints, ref bool longestPattern, ref List <MyPathOfPoints> listOfPaths, ref List <int> listOfPenultimate, ref List <int> listOfLast, ref StringBuilder fileOutput, ref bool toleranceOk, ref List <MyMatrAdj> listOfMatrAdj, ref List <MyComposedPatternOfComponents> listOfOutputPattern, ref List <MyComposedPatternOfComponents> listOfOutputPatternTwo, ref List <int> listOfIndicesOfLongestPath, ModelDoc2 SwModel, SldWorks SwApplication) { var branchesFirst = matrAdjToSee.matr.GetRow(startPointInd).Find(entry => entry == 1).ToList(); foreach (int branch1 in branchesFirst) { fileOutput.AppendLine("\n branch di StartPoint " + startPointInd + ": " + branch1); TwoPointsGivenPaths_Assembly_ComposedPatterns(matrAdjToSee, n, startPointInd, branch1, listOfPatternsOfComponents, listOfCentroids, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfOutputPattern, ref listOfOutputPatternTwo, ref listOfIndicesOfLongestPath, SwModel, SwApplication); if (toleranceOk == false) { return; } if (longestPattern == true) { return; } } }
//Se NumOfCent>=3: //Data una lista di centroid, crea matrici di adiacenza per ogni distanza tra centroid con occorrenza >=2 //Inoltre le ordine per numero di occorrenze decrescente public static List <MyMatrAdj> CreateMatrAdj(List <MyVertex> ListCentroid, ref StringBuilder fileOutput) { List <MyMatrAdj> MatrAdjList = new List <MyMatrAdj>(); int NumOfCent = ListCentroid.Count; if (NumOfCent < 3) //(forse questo controllo non serve perché utilizzo questa function se so già di avere n>=4) { fileOutput.AppendLine("There are not enough centroids in the list."); } else { for (int i = 0; i < NumOfCent - 1; i++) { for (int j = i + 1; j < NumOfCent; j++) { double dist = ListCentroid[i].Distance(ListCentroid[j]); int FoundIndex = MatrAdjList.FindIndex(matradj => Math.Abs(matradj.d - dist) < Math.Pow(10, -4)); if (FoundIndex == -1) //non è ancora stata creata la matrice di adiacenza per d { int[,] Matrix = new int[NumOfCent, NumOfCent]; //initialized to zero Matrix[i, j] = 1; Matrix[j, i] = 1; int NOccur = 1; MyMatrAdj NewMatrAdj = new MyMatrAdj(dist, Matrix, NOccur); MatrAdjList.Add(NewMatrAdj); } else //esiste già la matrice di adiacenza per d, è Found, la recupero { MatrAdjList[FoundIndex].matr[i, j] = 1; MatrAdjList[FoundIndex].matr[j, i] = 1; MatrAdjList[FoundIndex].nOccur += 1; } } } //I remove all the MatrAdjs with only one occurrence MatrAdjList.RemoveAll(m => m.nOccur == 1); //I order the list by creasing ordering respect to d, then by decreasing ordering respect to nOccur MatrAdjList = MatrAdjList.OrderBy(x => x.d).ThenByDescending(x => x.nOccur).ToList(); //I order the list by decreasing ordering respect to nOccur, then by creasing ordering respect to d //MatrAdjList = MatrAdjList.OrderByDescending(x => x.nOccur).ThenBy(x => x.d).ToList(); } return(MatrAdjList); }
//This function returns the list of paths obtained given the Start point. public static void OnePointGivenPaths(MyMatrAdj matrAdjToSee, int n, int startPointInd, List <MyRepeatedEntity> listOfReOnThisSurface, List <MyVertex> listCentroid, List <int> listOfExtremePoints, ref List <int> listOfSimplePoints_Copy, List <int> listOfMBPoints, ref bool longestPattern, ref List <MyPathOfPoints> listOfPaths, ref List <int> listOfPenultimate, ref List <int> listOfLast, ref StringBuilder fileOutput, ref bool toleranceOk, ref List <MyMatrAdj> listOfMatrAdj, ref List <MyGroupingSurface> listOfMyGroupingSurface, List <MyGroupingSurface> listOfInitialGroupingSurface, ref List <MyPattern> listOfOutputPattern, ref List <MyPattern> listOfOutputPatternTwo, ref List <int> listOfIndicesOfLongestPath) { List <int> BranchesFirst = matrAdjToSee.matr.GetRow(startPointInd).Find(entry => entry == 1).ToList(); //List<int> BranchesFirst = nInd.FindAll(ind => MatrAdjToSee.matr[StartPointInd, ind] == 1); foreach (int branch1 in BranchesFirst) { fileOutput.AppendLine("\n branch di StartPoint " + startPointInd + ": " + branch1); //List<List<int>> ListOfPathsThisBranch = TwoPointsGivenPaths(matrAdjToSee, n, startPointInd, branch1, listOfReOnThisSurface, listCentroid, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfMyGroupingSurface, listOfInitialGroupingSurface, ref listOfOutputPattern, ref listOfOutputPatternTwo, ref listOfIndicesOfLongestPath); //ListOfPathsOnePoint.AddRange(ListOfPathsThisBranch); if (toleranceOk == false) { return; } if (longestPattern == true) { return; } } //return ListOfPathsOnePoint; }//fine OnePointGivenPaths
public static void AddPathsFromNewCheckOfMB(MyMatrAdj matrAdjToSee, List <MyVertex> listCentroid, ref List <MyPathOfPoints> listOfPaths, List <int> listOfExtremePoints, List <int> listOfMBPoints, ref StringBuilder fileOutput, ref bool toleranceOk) { //Ultima ricerca: //individuo i path di length >3 e t.c. se num di MB nel path = s allora 0<s<length e //per ogni MB di tali path verifico che esista un path che contenga b1-MB-b2, con b1,b2 branch di MB. //[QUESTA PARTE SERVE IN PARTICOLARE PER I CASI "GRIGLIA"] if (listOfPaths.FindIndex(pathObject => (pathObject.path.Count > 3 && pathObject.path.Count(listOfMBPoints.Contains) < pathObject.path.Count && pathObject.path.Count(listOfMBPoints.Contains) > 0)) != -1) { var listOfPathsContainingMBToCheckAgain = new List <MyPathOfPoints>( listOfPaths.FindAll(pathObject => (pathObject.path.Count > 3 && pathObject.path.Count(listOfMBPoints.Contains) < pathObject.path.Count && pathObject.path.Count(listOfMBPoints.Contains) > 0))); var listOfMBToCheckAgain = new List <int>(listOfMBPoints.FindAll( mb => listOfPathsContainingMBToCheckAgain.FindIndex(pathObject => pathObject.path.Contains(mb)) != -1)); fileOutput.AppendLine("\n"); fileOutput.AppendLine("\n Path derivanti dal MB Check Again:"); foreach (var mb in listOfMBToCheckAgain) { List <int> branchesOfMB = matrAdjToSee.matr.GetRow(mb).Find(entry => entry == 1).ToList(); //indici dei branch di mb int lengthOfBranchesList = branchesOfMB.Count; for (var i = 0; i < lengthOfBranchesList - 1; i++) { for (var j = i + 1; j < lengthOfBranchesList; j++) { var branch1 = branchesOfMB[i]; var branch2 = branchesOfMB[j]; if (!(listOfExtremePoints.Contains(branch1)) && !(listOfExtremePoints.Contains(branch2))) //perché se uno dei due branch è un estremo sono sicura che un path contenente branch1-mb-branch2 esiste { if (listOfPaths.FindIndex(pathObject => (pathObject.path.Contains(branch1) && pathObject.path.Contains(mb) && pathObject.path.Contains(branch2))) == -1) //se non esiste path contenente branch1-mb-branch2 { List <int> currentPath; MyPathGeometricObject pathCurve; if (listCentroid[branch2].Lieonline(GeometricUtilities.FunctionsLC.LinePassingThrough(listCentroid[mb], listCentroid[branch1]))) { currentPath = ThreePointsGivenPathsLine(matrAdjToSee, listCentroid, listOfExtremePoints, branch1, mb, branch2, ref fileOutput, ref toleranceOk, out pathCurve); } else { currentPath = ThreePointsGivenPathsCircum(matrAdjToSee, listCentroid, listOfExtremePoints, branch1, mb, branch2, ref fileOutput, ref toleranceOk, out pathCurve); } //Verifica LongestPattern? //se nel path che ho creato ci fossero dei MB li avrei già presi, //se ci fossero dei simple non ancora toccati li avrei già presi, //sono quasi certa che il path sia composto da punti già percorsi almeno una volta //(sicuramente almeno una volta i branch del MB sono stati percorsi)... //----> Non faccio il salvataggio dei penultimi punti. var newPathObject = new MyPathOfPoints(currentPath, pathCurve); listOfPaths.Add(newPathObject); } } } } } } }// fine AddPathsFromNewCheckOfMB
//Crea il massimo path LINEA a partire dai 3 punti dati public static List <int> ThreePointsGivenPathsLine(MyMatrAdj MatrAdjToSee, List <MyVertex> ListCentroid, List <int> ListOfExtremePoints, int Point1, int Point2, int Point3, ref StringBuilder fileOutput, ref bool ToleranceOk, out MyPathGeometricObject pathCurve) { #region VERSION 1: the original, it is ok //var nameFile = "ContaElementiPath.txt"; //List<int> Path = new List<int>(); //Path.Add(Point1); //Path.Add(Point2); //Path.Add(Point3); //KLdebug.Print("point1 = " + Point1, nameFile); //KLdebug.Print("point2 = " + Point2, nameFile); //KLdebug.Print("point1 = " + Point3, nameFile); //MyLine linePath = FunctionsLC.LinePassingThrough(ListCentroid[Point2], ListCentroid[Point3]); ////procedo nella direzione Point2-Point3 //List<int> BranchesThird = MatrAdjToSee.matr.GetRow(Point3).Find(entry => entry == 1).ToList(); //cerco tra questi //BranchesThird.Remove(Point2); //KLdebug.Print("Num of elementi in BranchesThird (1^ volta) = " + BranchesThird.Count, nameFile); //foreach (int ind in BranchesThird) //{ // KLdebug.Print("- " + ind, nameFile); //} //int Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); //while (Next != -1) //{ // // Check if the tolerance is too rough // int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; // if (NumOfFound == 1) // { // int NextInd = BranchesThird[Next]; // BranchesThird.Clear(); // BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi // KLdebug.Print("Num of elementi in BranchesThird = " + BranchesThird.Count, nameFile); // foreach (int ind in BranchesThird) // { // KLdebug.Print("- " + ind, nameFile); // } // BranchesThird.Remove(Path[Path.Count - 1]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in coda), perché se no tornerei indietro // KLdebug.Print("Path.count = " + Path.Count, nameFile); // Path.Add(NextInd); //aggiungo in coda al path // KLdebug.Print("Aggiunto al path: - " + NextInd, nameFile); // KLdebug.Print("Path.count dopo aggiunta = " + Path.Count, nameFile); // Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); // KLdebug.Print(" ", nameFile); // } // else // { // //End the execution in the higher levels // ToleranceOk = false; // pathCurve = null; // return Path; // } //} //#region Check if I can invert the direction of expansion on not ////se Point1 non era un Extreme point, inverto la direzione procedendo verso Point2-Point1 //if (!(ListOfExtremePoints.Contains(Point1))) //{ // BranchesThird.Clear(); // BranchesThird = MatrAdjToSee.matr.GetRow(Point1).Find(entry => entry == 1).ToList(); //cerco tra questi // BranchesThird.Remove(Point2); // Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); // //uso FindIndex perché mi restituisce -1 se non trova // while (Next != -1) // { // // Check if the tolerance is too rough // int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; // if (NumOfFound == 1) // { // int NextInd = BranchesThird[Next]; // BranchesThird.Clear(); // BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi // BranchesThird.Remove(Path[0]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in testa), perché se no tornerei indietro // Path.Insert(0, NextInd); //aggiungo in testa al path // Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); // } // else // { // //End the execution in the higher levels // ToleranceOk = false; // pathCurve = null; // return Path; // } // } //} //#endregion //fileOutput.AppendLine("\n Nuovo path retta:"); //foreach (int ind in Path) //{ // fileOutput.AppendLine(" - " + ind); //} //pathCurve = linePath; //return Path; #endregion #region VERSION 2: ok but not very compact /* var nameFile = "ContaElementiPath.txt"; * * List<int> Path = new List<int>(); * * Path.Add(Point1); * Path.Add(Point2); * Path.Add(Point3); * KLdebug.Print("point1 = " + Point1, nameFile); * KLdebug.Print("point2 = " + Point2, nameFile); * KLdebug.Print("point1 = " + Point3, nameFile); * * KLdebug.Print("Matr distance = " + MatrAdjToSee.d, nameFile); * KLdebug.Print("Matrice dimension = " + MatrAdjToSee.matr.GetLength(0), nameFile); * var line = string.Format( * "Matrice :\n" + * "{0} {1} {2} {3}\n" + * "{4} {5} {6} {7}\n" + * "{8} {9} {10} {11}\n"+ * "{12} {13} {14} {15}\n\n", * * MatrAdjToSee.matr[0, 0], MatrAdjToSee.matr[0, 1], MatrAdjToSee.matr[0, 2], MatrAdjToSee.matr[0, 3], * MatrAdjToSee.matr[1, 0], MatrAdjToSee.matr[1, 1], MatrAdjToSee.matr[1, 2], MatrAdjToSee.matr[1, 3], * MatrAdjToSee.matr[2, 0], MatrAdjToSee.matr[2, 1], MatrAdjToSee.matr[2, 2], MatrAdjToSee.matr[2, 3], * MatrAdjToSee.matr[3, 0], MatrAdjToSee.matr[3, 1], MatrAdjToSee.matr[3, 2], MatrAdjToSee.matr[3, 3] * ); * KLdebug.Print(line, nameFile); * * MyLine linePath = FunctionsLC.LinePassingThrough(ListCentroid[Point2], ListCentroid[Point3]); * int NextInd; * * //procedo nella direzione Point2-Point3 * List<int> BranchesThird = MatrAdjToSee.matr.GetRow(Point3).Find(entry => entry == 1).ToList(); //cerco tra questi * BranchesThird.Remove(Point2); * * KLdebug.Print("Branches di " + Point3 + " :", nameFile); * foreach (int ind in BranchesThird) * { * KLdebug.Print("- " + ind, nameFile); * } * * int Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); * int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; * * if (NumOfFound == 1) * { * NextInd = BranchesThird[Next]; * Path.Add(NextInd); //aggiungo in coda al path * KLdebug.Print("Aggiunto al path (1^ volta) : - " + NextInd, nameFile); * KLdebug.Print("Path dopo aggiunta: ", nameFile); * foreach (int ind in Path) * { * KLdebug.Print("- " + ind, nameFile); * } * * BranchesThird.Clear(); * BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi * BranchesThird.Remove(Path[Path.Count - 2]); * KLdebug.Print("Rimosso dai branch (1^ volta) : - " + Path[Path.Count - 2], nameFile); * * KLdebug.Print("Branches (1^ volta)" + NextInd + " :", nameFile); * foreach (int ind in BranchesThird) * { * KLdebug.Print("- " + ind, nameFile); * } * Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); * KLdebug.Print(" ", nameFile); * * * while (Next != -1) * { * KLdebug.Print("(Entro nel while)", nameFile); * // Check if the tolerance is too rough * NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; * if (NumOfFound == 1) * { * NextInd = BranchesThird[Next]; * BranchesThird.Clear(); * BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi * BranchesThird.Remove(Path[Path.Count - 1]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in coda), perché se no tornerei indietro * KLdebug.Print("Rimosso dai branch: - " + Path[Path.Count - 2], nameFile); * * KLdebug.Print("Branches di " + NextInd + " :", nameFile); * foreach (int ind in BranchesThird) * { * KLdebug.Print("- " + ind, nameFile); * } * * Path.Add(NextInd); //aggiungo in coda al path * KLdebug.Print("Aggiunto al path: - " + NextInd, nameFile); * KLdebug.Print("Path dopo aggiunta: " + Path.Count, nameFile); * foreach (int ind in Path) * { * KLdebug.Print("- " + ind, nameFile); * } * Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); * KLdebug.Print(" ", nameFile); * * } * else * { * //End the execution in the higher levels * ToleranceOk = false; * pathCurve = null; * return Path; * } * * * } * } * #region Check if I can invert the direction of expansion on not * //se Point1 non era un Extreme point, inverto la direzione procedendo verso Point2-Point1 * if (!(ListOfExtremePoints.Contains(Point1))) * { * BranchesThird.Clear(); * BranchesThird = MatrAdjToSee.matr.GetRow(Point1).Find(entry => entry == 1).ToList(); //cerco tra questi * BranchesThird.Remove(Point2); * Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); * //uso FindIndex perché mi restituisce -1 se non trova * while (Next != -1) * { * // Check if the tolerance is too rough * NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; * if (NumOfFound == 1) * { * NextInd = BranchesThird[Next]; * BranchesThird.Clear(); * BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi * BranchesThird.Remove(Path[0]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in testa), perché se no tornerei indietro * Path.Insert(0, NextInd); //aggiungo in testa al path * Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); * } * else * { * //End the execution in the higher levels * ToleranceOk = false; * pathCurve = null; * return Path; * } * * } * } #endregion * * fileOutput.AppendLine("\n Nuovo path retta:"); * foreach (int ind in Path) * { * fileOutput.AppendLine(" - " + ind); * } * pathCurve = linePath; * return Path; */ #endregion //VERSION 3: Ok and more compact List <int> Path = new List <int>(); Path.Add(Point1); Path.Add(Point2); Path.Add(Point3); MyLine linePath = FunctionsLC.LinePassingThrough(ListCentroid[Point2], ListCentroid[Point3]); //procedo nella direzione Point2-Point3 List <int> BranchesThird = MatrAdjToSee.matr.GetRow(Point3).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Point2); int Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); while (Next != -1) { // Check if the tolerance is too rough int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; if (NumOfFound == 1) { int NextInd = BranchesThird[Next]; Path.Add(NextInd); //aggiungo in coda al path BranchesThird.Clear(); BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Path[Path.Count - 2]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in coda), perché se no tornerei indietro Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); } else { //End the execution in the higher levels ToleranceOk = false; pathCurve = null; return(Path); } } #region Check if I can invert the direction of expansion on not //se Point1 non era un Extreme point, inverto la direzione procedendo verso Point2-Point1 if (!(ListOfExtremePoints.Contains(Point1))) { BranchesThird.Clear(); BranchesThird = MatrAdjToSee.matr.GetRow(Point1).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Point2); Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); //uso FindIndex perché mi restituisce -1 se non trova while (Next != -1) { // Check if the tolerance is too rough int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)).Count; if (NumOfFound == 1) { int NextInd = BranchesThird[Next]; BranchesThird.Clear(); BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Path[0]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in testa), perché se no tornerei indietro Path.Insert(0, NextInd); //aggiungo in testa al path Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieonline(linePath)); } else { //End the execution in the higher levels ToleranceOk = false; pathCurve = null; return(Path); } } } #endregion fileOutput.AppendLine("\n Nuovo path retta:"); foreach (int ind in Path) { fileOutput.AppendLine(" - " + ind); } pathCurve = linePath; return(Path); } //fine ThreePointsGivenPathsLine
// This function updates the list of paths adding the paths raising from // the given 1st and 2nd seed set points (FOR ASSEMBLY) public static void TwoPointsGivenPaths_Assembly_ComposedPatterns(MyMatrAdj matrAdjToSee, int n, int startPointInd, int secondPointInd, List <MyPatternOfComponents> listOfPatternsOfComponents, List <MyVertex> listOfCentroids, List <int> listOfExtremePoints, ref List <int> listOfSimplePoints_Copy, List <int> listOfMBPoints, ref bool longestPattern, ref List <MyPathOfPoints> listOfPaths, ref List <int> listOfPenultimate, ref List <int> listOfLast, ref StringBuilder fileOutput, ref bool toleranceOk, ref List <MyMatrAdj> listOfMatrAdj, ref List <MyComposedPatternOfComponents> listOfOutputComposedPattern, ref List <MyComposedPatternOfComponents> listOfOutputComposedPatternTwo, ref List <int> listOfIndicesOfLongestPath, ModelDoc2 SwModel, SldWorks SwApplication) { if (listOfExtremePoints.Contains(secondPointInd)) //If the branch is an ExtremePoint, I treat it in a special way as I have not //the path equation yet. So I guide the 3rd point search. { //I come back, so I look what are the branches of the StartPoint List <int> branchesSecond = matrAdjToSee.matr.GetRow(startPointInd).Find(entry => entry == 1).ToList(); branchesSecond.Remove(secondPointInd); foreach (var branch2 in branchesSecond) { var newMyPathOfPoints = new MyPathOfPoints(); //if (SecondPointInd(extreme), StartPointInd(MB), branch2 don't belong to an existing path in ListOfPaths) if (listOfPaths.FindIndex(pathObject => (pathObject.path.Contains(secondPointInd) && pathObject.path.Contains(startPointInd) && pathObject.path.Contains(branch2))) == -1) { List <int> currentPath; MyPathGeometricObject pathCurve; if (listOfCentroids[branch2].Lieonline(FunctionsLC.LinePassingThrough(listOfCentroids[startPointInd], listOfCentroids[secondPointInd]))) { currentPath = Part.PathCreation_Part.Functions.ThreePointsGivenPathsLine(matrAdjToSee, listOfCentroids, listOfExtremePoints, secondPointInd, startPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); // Notice that expansion will procede only in one direction } else { currentPath = Part.PathCreation_Part.Functions.ThreePointsGivenPathsCircum(matrAdjToSee, listOfCentroids, listOfExtremePoints, secondPointInd, startPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); // Notice that expansion will procede only in one direction } if (toleranceOk == false) { return; } //If I have found a complete circumference I delete the repeated centroid index: if (currentPath[0] == currentPath[currentPath.Count - 1]) { currentPath.RemoveAt(currentPath.Count - 1); } newMyPathOfPoints.path = currentPath; newMyPathOfPoints.pathGeometricObject = pathCurve; listOfPaths.Add(newMyPathOfPoints); fileOutput.AppendLine("Aggiunto alla lista nuovo path: "); fileOutput.AppendLine(" -numero di baricentri:" + newMyPathOfPoints.path.Count); if (pathCurve.GetType() == typeof(MyLine)) { fileOutput.AppendLine(" -tipo di path: retta"); fileOutput.AppendLine(""); } else { fileOutput.AppendLine(" -tipo di path: criconferenza"); fileOutput.AppendLine(""); } //If a path of length n or n-1 is found, I move up the geometrical verify to see //if the process can be stopped at this point (sufficiently satisfying result on this GS) int m = currentPath.Count; if (m == n || m == n - 1) { fileOutput.AppendLine("\n Trovato path che potrebbe dare un Longest Pattern: VERIFICO"); // Removing of the path from the list: //this is done because if the pattern is verified the updating phase (in particular //referred to the part of list of paths updating) will consider all the paths existing //in the list of paths (so also the current long one) and the updating would be //long and useless (we would try to compare the current path to itself). listOfPaths.RemoveAt(listOfPaths.Count - 1); if (newMyPathOfPoints.pathGeometricObject.GetType() == typeof(MyLine)) { if (AssemblyUtilities_ComposedPatterns.LC_AssemblyTraverse.GetComposedPatternsFromPathLine_Assembly(newMyPathOfPoints, listOfPatternsOfComponents, ref listOfPaths, ref listOfMatrAdj, ref listOfOutputComposedPattern, ref listOfOutputComposedPatternTwo)) { fileOutput.AppendLine("\n è longestPattern verificato!! "); longestPattern = true; return; } else { fileOutput.AppendLine("\n longestPattern NON verificato!! "); listOfPaths.Add(newMyPathOfPoints); // Updating of the list of Simple points not yet passed through: var ListOfPaths_copy = new List <MyPathOfPoints>(listOfPaths); listOfSimplePoints_Copy.RemoveAll( point => ListOfPaths_copy[ListOfPaths_copy.Count - 1].path.Contains(point)); Part.PathCreation_Part.Functions.UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, currentPath); listOfIndicesOfLongestPath.Add(listOfPaths.IndexOf(newMyPathOfPoints)); } } else //newMyPathOfCentroids.pathGeometricObject.GetType() == typeof (MyCircumForPath) { if (AssemblyUtilities_ComposedPatterns.LC_AssemblyTraverse.GetComposedPatternsFromPathCircum_Assembly(newMyPathOfPoints, listOfPatternsOfComponents, ref listOfPaths, ref listOfMatrAdj, ref listOfOutputComposedPattern, ref listOfOutputComposedPatternTwo, SwApplication, ref fileOutput)) { fileOutput.AppendLine("\n è longestPattern verificato!! "); longestPattern = true; return; } else { fileOutput.AppendLine("\n longestPattern NON verificato!! "); listOfPaths.Add(newMyPathOfPoints); // Updating of the list of Simple points not yet passed through: var ListOfPaths_copy = new List <MyPathOfPoints>(listOfPaths); listOfSimplePoints_Copy.RemoveAll( point => ListOfPaths_copy[ListOfPaths_copy.Count - 1].path.Contains(point)); Part.PathCreation_Part.Functions.UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, currentPath); listOfIndicesOfLongestPath.Add(listOfPaths.IndexOf(newMyPathOfPoints)); } } } else { Part.PathCreation_Part.Functions.UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, currentPath); } } } } else // cioè listOfMBPoints.Contains(SecondPointInd) || ListOfSimplePoints.Contains(SecondPointInd) { List <int> branchesSecond = matrAdjToSee.matr.GetRow(secondPointInd).Find(entry => entry == 1).ToList(); branchesSecond.Remove(startPointInd); //I remove the startingPoint not to come back in the start direction foreach (var branch2 in branchesSecond) { var newMyPathOfPoints = new MyPathOfPoints(); // if (StartPointInd, SecondPointInd, branch2 don't belong to an existing path in ListOfPaths ) if (listOfPaths.FindIndex(pathObject => (pathObject.path.Contains(startPointInd) && pathObject.path.Contains(secondPointInd) && pathObject.path.Contains(branch2))) == -1) { List <int> currentPath; MyPathGeometricObject pathCurve; if (listOfCentroids[branch2].Lieonline(FunctionsLC.LinePassingThrough(listOfCentroids[startPointInd], listOfCentroids[secondPointInd]))) { currentPath = Part.PathCreation_Part.Functions.ThreePointsGivenPathsLine(matrAdjToSee, listOfCentroids, listOfExtremePoints, startPointInd, secondPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); } else { currentPath = Part.PathCreation_Part.Functions.ThreePointsGivenPathsCircum(matrAdjToSee, listOfCentroids, listOfExtremePoints, startPointInd, secondPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); } if (toleranceOk == false) { return; } //If I have found a complete circumference I delete the repeated centroid index: if (currentPath[0] == currentPath[currentPath.Count - 1]) { currentPath.RemoveAt(currentPath.Count - 1); } newMyPathOfPoints.path = currentPath; newMyPathOfPoints.pathGeometricObject = pathCurve; listOfPaths.Add(newMyPathOfPoints); fileOutput.AppendLine("Aggiunto alla lista nuovo path: "); fileOutput.AppendLine(" -numero di baricentri:" + newMyPathOfPoints.path.Count); if (pathCurve.GetType() == typeof(MyLine)) { fileOutput.AppendLine(" -tipo di path: retta"); } else { fileOutput.AppendLine(" -tipo di path: circonferenza"); } //If a path of length n or n-1 is found, I move up the geometrical verify to see //if the process can be stopped at this point (sufficiently satisfying result on this GS) int m = currentPath.Count; if (m == n || m == n - 1) { fileOutput.AppendLine("\n Trovato path che potrebbe dare un Longest Pattern: VERIFICO"); // Removing of the path from the list: listOfPaths.RemoveAt(listOfPaths.Count - 1); if (newMyPathOfPoints.pathGeometricObject.GetType() == typeof(MyLine)) { if (AssemblyUtilities_ComposedPatterns.LC_AssemblyTraverse.GetComposedPatternsFromPathLine_Assembly(newMyPathOfPoints, listOfPatternsOfComponents, ref listOfPaths, ref listOfMatrAdj, ref listOfOutputComposedPattern, ref listOfOutputComposedPatternTwo)) { fileOutput.AppendLine("\n è longestPattern verificato!! "); longestPattern = true; return; } else { fileOutput.AppendLine("\n longestPattern NON verificato!! "); listOfPaths.Add(newMyPathOfPoints); // Updating of the list of Simple points not yet passed through: var ListOfPaths_copy = new List <MyPathOfPoints>(listOfPaths); listOfSimplePoints_Copy.RemoveAll( point => ListOfPaths_copy[ListOfPaths_copy.Count - 1].path.Contains(point)); Part.PathCreation_Part.Functions.UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, currentPath); listOfIndicesOfLongestPath.Add(listOfPaths.IndexOf(newMyPathOfPoints)); } } else //newMyPathOfCentroids.pathGeometricObject.GetType() == typeof (MyCircumForPath) { if (AssemblyUtilities_ComposedPatterns.LC_AssemblyTraverse.GetComposedPatternsFromPathCircum_Assembly(newMyPathOfPoints, listOfPatternsOfComponents, ref listOfPaths, ref listOfMatrAdj, ref listOfOutputComposedPattern, ref listOfOutputComposedPatternTwo, SwApplication, ref fileOutput)) { fileOutput.AppendLine("\n è longestPattern verificato!! "); longestPattern = true; return; } else { fileOutput.AppendLine("\n longestPattern NON verificato!! "); listOfPaths.Add(newMyPathOfPoints); // Updating of the list of Simple points not yet passed through: var ListOfPaths_copy = new List <MyPathOfPoints>(listOfPaths); listOfSimplePoints_Copy.RemoveAll( point => ListOfPaths_copy[ListOfPaths_copy.Count - 1].path.Contains(point)); Part.PathCreation_Part.Functions.UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, currentPath); listOfIndicesOfLongestPath.Add(listOfPaths.IndexOf(newMyPathOfPoints)); } } } else { Part.PathCreation_Part.Functions.UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, currentPath); } } } } }
public static void FindComposedPatternsOfComponents( List <MyPatternOfComponents> listOfPatternsOfComponentsLine, List <MyPatternOfComponents> listOfPatternsOfComponentsCircum, out List <MyComposedPatternOfComponents> listOfOutputComposedPattern, out List <MyComposedPatternOfComponents> listOfOutputComposedPatternTwo, ModelDoc2 SwModel, SldWorks mySwApplication, ref StringBuilder fileOutput) { var toleranceOk = true; var listOfComposedPattern = new List <MyComposedPatternOfComponents>(); var listOfComposedPatternTwo = new List <MyComposedPatternOfComponents>(); // >>>>>>> LINEAR CASE: //first I group patterns by same length and same distance: var listOfListsOfCoherentPatternsLine = GroupFoundPatternsOfComponentsOfTypeLine( listOfPatternsOfComponentsLine, mySwApplication); //Then I group coherent patterns in subgroups of parallel patterns: foreach (var list in listOfListsOfCoherentPatternsLine) { //Grouping in lists of parallel patterns var listOfListsOfParallelPatterns = GroupPatternsOfComponentsInParallel(list); var numOfListsOfParallelPatterns = listOfListsOfParallelPatterns.Count; if (list.Count == 2) { //I verify if a composed pattern with these 2 patterns has already been created //in another GS: if (ComposedPatternOfComponentsOfLength2AlreadyExists(listOfComposedPatternTwo, list) == false) { //if a composed pattern does not exist yet AND //the 2 patterns are not parallel, I verify if it is REFLECTION: if (numOfListsOfParallelPatterns == 0) { //if (IsReflectionTwoPatterns(list[0], list[1])) //{ // KLdebug.Print("I 2 Pattern sono legate da RIFLESSIONE!", nameFile); // var typeOfNewComposedPattern = "Composed REFLECTION of length 2"; // BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, // ref listOfComposedPattern, ref listOfComposedPatternTwo, // ref listOfGroupingSurfaceForPatterns, list); //} } else //if a composed pattern does not exist yet AND //the 2 patterns are parallel, I verify if it is TRANSLATION: { if (IsTranslationTwoPatternsOfComponents(list[0], list[1])) { var typeOfNewComposedPattern = "Composed TRANSLATION of length 2"; BuildNewComposedPatternOfComponentsOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, list); } } } } else { foreach (var listOfParallelPatterns in listOfListsOfParallelPatterns) { if (listOfParallelPatterns.Count == 2) { //I verify if a composed pattern with these 2 patterns has already been created //in another GS: if (ComposedPatternOfComponentsOfLength2AlreadyExists(listOfComposedPatternTwo, list)) { } else { if (IsTranslationTwoPatternsOfComponents(listOfParallelPatterns[0], listOfParallelPatterns[1])) { var typeOfNewComposedPattern = "Composed TRANSLATION of length 2"; BuildNewComposedPatternOfComponentsOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, listOfParallelPatterns); } } } else //(listOfParallelPatterns.Count > 2) { var listOfPatternCentroids = listOfParallelPatterns.Select(pattern => pattern.patternCentroid).ToList(); fileOutput.AppendLine(""); fileOutput.AppendLine(" >>>> CREATION OF ADJECENCY MATRICES FOR COMPOSED PATTERNS:"); var listOfMyMatrAdj = Functions.CreateMatrAdj(listOfPatternCentroids, ref fileOutput); var maxPath = false; //it is TRUE if the maximum Pattern is found, FALSE otherwise. while (listOfMyMatrAdj.Count > 0 && maxPath == false && toleranceOk) { var currentMatrAdj = new MyMatrAdj(listOfMyMatrAdj[0].d, listOfMyMatrAdj[0].matr, listOfMyMatrAdj[0].nOccur); listOfMyMatrAdj.Remove(listOfMyMatrAdj[0]); //NOTA: forse la mia MatrAdj non deve essere rimossa ma conservata, //soprattutto nel caso in cui si presenta onlyShortPath = true //(non avrebbe senso cancellarla, ma conservarla per la ricerca di path //di 2 RE). List <MyPathOfPoints> listOfPathsOfCentroids; bool onlyShortPaths; maxPath = PathCreation_Assembly_ComposedPatterns.Functions.FindPaths_Assembly_ComposedPatterns(currentMatrAdj, listOfParallelPatterns, ref fileOutput, out listOfPathsOfCentroids, out onlyShortPaths, ref toleranceOk, ref listOfMyMatrAdj, ref listOfComposedPattern, ref listOfComposedPatternTwo, SwModel, mySwApplication); if (toleranceOk) { if (listOfPathsOfCentroids != null) { if (maxPath == false) { if (onlyShortPaths == false) { GetComposedPatternsFromListOfPathsLine_Assembly(listOfPathsOfCentroids, listOfParallelPatterns, ref listOfMyMatrAdj, ref listOfComposedPattern, ref listOfComposedPatternTwo, mySwApplication, ref fileOutput); } else { //non faccio niente e li rimetto in gioco per } } } } else { listOfOutputComposedPattern = listOfComposedPattern; listOfOutputComposedPatternTwo = listOfComposedPatternTwo; return; } } } } //Now coherent linear patterns that have not been set in a composed pattern yet //are examined to see if they consitute any rotation composed pattern: list.RemoveAll( pattern => listOfComposedPattern.FindIndex( composedPattern => composedPattern.ListOfMyPatternOfComponents.FindIndex( patternInComposedPattern => patternInComposedPattern.idMyPattern == pattern.idMyPattern) != -1) != -1); if (list.Count != 0) { if (list.Count == 2) { // >>> POSSIBLE REFLECTION CAN EXIST //I verify if a composed pattern with these 2 patterns has already been created //in another GS: if (ComposedPatternOfComponentsOfLength2AlreadyExists(listOfComposedPatternTwo, list)) { } } else { var listOfPatternCentroids1 = list.Select(pattern => pattern.patternCentroid).ToList(); fileOutput.AppendLine(""); fileOutput.AppendLine(" >>>> CREATION OF ADJECENCY MATRICES FOR COMPOSED PATTERNS:"); var listOfMyMatrAdj1 = Functions.CreateMatrAdj(listOfPatternCentroids1, ref fileOutput); var maxPath = false; //it is TRUE if the maximum Pattern is found, FALSE otherwise. while (listOfMyMatrAdj1.Count > 0 && maxPath == false && toleranceOk) { var currentMatrAdj = new MyMatrAdj(listOfMyMatrAdj1[0].d, listOfMyMatrAdj1[0].matr, listOfMyMatrAdj1[0].nOccur); listOfMyMatrAdj1.Remove(listOfMyMatrAdj1[0]); //NOTA: forse la mia MatrAdj non deve essere rimossa ma conservata, //soprattutto nel caso in cui si presenta onlyShortPath = true //(non avrebbe senso cancellarla, ma conservarla per la ricerca di path //di 2 RE). List <MyPathOfPoints> listOfPathsOfCentroids1; bool onlyShortPaths1; var maxPath1 = PathCreation_Assembly_ComposedPatterns.Functions.FindPaths_Assembly_ComposedPatterns(currentMatrAdj, list, ref fileOutput, out listOfPathsOfCentroids1, out onlyShortPaths1, ref toleranceOk, ref listOfMyMatrAdj1, ref listOfComposedPattern, ref listOfComposedPatternTwo, SwModel, mySwApplication); if (toleranceOk) { if (listOfPathsOfCentroids1 != null) { //I ignore every linear path (I look for composed rotational patterns now): var listOfCircularPaths = listOfPathsOfCentroids1.FindAll( path => path.pathGeometricObject.GetType() == typeof(MyCircumForPath)) .ToList(); if (maxPath1 == false) { if (onlyShortPaths1 == false) { GetComposedPatternsFromListOfPathsLine_Assembly(listOfCircularPaths, list, ref listOfMyMatrAdj1, ref listOfComposedPattern, ref listOfComposedPatternTwo, mySwApplication, ref fileOutput); } else { //non faccio niente e li rimetto in gioco per } } } } } } } } } listOfOutputComposedPattern = listOfComposedPattern; listOfOutputComposedPatternTwo = listOfComposedPatternTwo; }
public static bool FindPaths_Assembly(MyMatrAdj matrAdjToSee, List <MyRepeatedComponent> listOfComponents, ref StringBuilder fileOutput, out List <MyPathOfPoints> listOfPathsOfPoints, out bool onlyShortPaths, ref bool toleranceOk, ref List <MyMatrAdj> listOfMatrAdj, ref List <MyPatternOfComponents> listOfOutputPattern, ref List <MyPatternOfComponents> listOfOutputPatternTwo) { int n = matrAdjToSee.matr.GetLength(0); bool longestPattern = false; var listOfIndicesOfLongestPath = new List <int>(); //to keep in mind the index of the LongestPath if it is found during the process: I can't delete it from the list //immediately because I need it to remember the points I have already passed through. //Then at the end I delete this path from the list because it is geometrically verified in the process //(and if I have to delete it, it means that is not a real geometric pattern). var listOfPaths = new List <MyPathOfPoints>(); var listOfOrigins = new List <MyVertex>(listOfComponents.Select(comp => comp.Origin).ToList()); List <int> listOfExtremePoints = new List <int>(); //list of Extreme points List <int> listOfSimplePoints = new List <int>(); //list of Simple points List <int> listOfMBPoints = new List <int>(); //list of Multibranch points // We classify the points involved in the current adjacency matrix: Part.PathCreation_Part.Functions.ClassifyComponents(matrAdjToSee, n, ref listOfExtremePoints, ref listOfSimplePoints, ref listOfMBPoints); //Work copies of the point lists: List <int> listOfSimplePoints_Copy = new List <int>(listOfSimplePoints); List <int> listOfMBPoints_Copy = new List <int>(listOfMBPoints); List <int> listOfPenultimate = new List <int>(); List <int> listOfLast = new List <int>(); while (listOfMBPoints_Copy.Count > 0) { int startPointInd = listOfMBPoints_Copy[0]; fileOutput.AppendLine("\n StartPoint MB:" + startPointInd); OnePointGivenPaths_Assembly(matrAdjToSee, n, startPointInd, listOfComponents, listOfOrigins, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfOutputPattern, ref listOfOutputPatternTwo, ref listOfIndicesOfLongestPath); if (toleranceOk == false) { fileOutput.AppendLine("\n \n WARNING: the program has been interrupted."); fileOutput.AppendLine("The tolerance level is too rough: put a lower tolerance."); listOfPathsOfPoints = null; onlyShortPaths = false; return(false); } if (longestPattern == true) { fileOutput.AppendLine("\n LongestPattern = true"); listOfPathsOfPoints = listOfPaths; onlyShortPaths = false; return(true); } listOfMBPoints_Copy.Remove(startPointInd); } //At this point we exit from WHILE because ListOfMBPoints_copy.Count == 0: //now the MB points that could be StartPoint are finished or they have never existed if (listOfMBPoints.Count == 0 && listOfSimplePoints.Count > 0) // i.e. MB points have never existed (never entered the WHILE cycle) { // and there exists at connected component of at least 3 points (-> there esists a simple point) //I must start the "expansion" from a simple point! fileOutput.AppendLine("Non esistono MB points."); fileOutput.AppendLine(""); var startPointInd = listOfSimplePoints[0]; //I take the first Simple point of the list OnePointGivenPaths_Assembly(matrAdjToSee, n, startPointInd, listOfComponents, listOfOrigins, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfOutputPattern, ref listOfOutputPatternTwo, ref listOfIndicesOfLongestPath); if (toleranceOk == false) { fileOutput.AppendLine("\n \n WARNING: the program has been interrupted."); fileOutput.AppendLine("The tolerance level is too rough: put a lower tolerance."); listOfPathsOfPoints = null; onlyShortPaths = false; return(false); } if (longestPattern == true) { fileOutput.AppendLine("\n LongestPattern = true"); listOfPathsOfPoints = listOfPaths; onlyShortPaths = false; return(true); } } else //here there are 3 cases: T+F I have to exit because I only have connected components of 2 centroids; //F+T and F+F I am sure I have at least a path created (penultimate points set exists), there is nothing to do in this case. { if (listOfMBPoints.Count == 0 && listOfSimplePoints.Count == 0) //T+F { listOfPathsOfPoints = null; onlyShortPaths = true; return(false); } } fileOutput.AppendLine(""); fileOutput.AppendLine("Lista dei penultimi punti alla fine dei MB come StartPoint:"); foreach (int ind in listOfPenultimate) { fileOutput.AppendLine("* " + ind); } //At this point at least one path has been created. The list of penultimate point is surely not void. //I remove all Simple points I already passed through up to now. listOfSimplePoints_Copy.RemoveAll( point => listOfPaths.FindIndex(pathObject => pathObject.path.Contains(point)) != -1); fileOutput.AppendLine(""); fileOutput.AppendLine("Lista Simple Point per cui non si è ancora passati:"); foreach (int ind in listOfSimplePoints_Copy) { fileOutput.AppendLine("* " + ind); } // Now, if there is a penultimate point available in the list I use it as StartPoint // else I use a Simple Point not belonging to any path (the point is in ListOfSimplePoints_copy) int numOfPenultimate = listOfPenultimate.Count; fileOutput.AppendLine(""); fileOutput.AppendLine("Numero di penultimi punti: " + numOfPenultimate); int numOfSimple = listOfSimplePoints_Copy.Count; fileOutput.AppendLine(""); fileOutput.AppendLine("Numero di Simple punti in cui non si è ancora passati: " + numOfPenultimate + numOfSimple); while (numOfPenultimate + numOfSimple > 0) { if (numOfPenultimate > 0) { // I look for a path with the first available "penultimate point" as StartPoint and I move towards of the relative "last point" fileOutput.AppendLine(" uso un penultimo punto: " + listOfPenultimate[0] + " verso " + listOfLast[0]); int startPointInd = listOfPenultimate[0]; int secondPointInd = listOfLast[0]; TwoPointsGivenPaths_Assembly(matrAdjToSee, n, startPointInd, secondPointInd, listOfComponents, listOfOrigins, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfOutputPattern, ref listOfOutputPatternTwo, ref listOfIndicesOfLongestPath); listOfPenultimate.Remove(startPointInd); listOfLast.Remove(secondPointInd); } else // => NumOfSimple > 0 { fileOutput.AppendLine(" uso un Simple punto: " + listOfSimplePoints_Copy[0]); var startPointInd = listOfSimplePoints_Copy[0]; OnePointGivenPaths_Assembly(matrAdjToSee, n, startPointInd, listOfComponents, listOfOrigins, listOfExtremePoints, ref listOfSimplePoints_Copy, listOfMBPoints, ref longestPattern, ref listOfPaths, ref listOfPenultimate, ref listOfLast, ref fileOutput, ref toleranceOk, ref listOfMatrAdj, ref listOfOutputPattern, ref listOfOutputPatternTwo, ref listOfIndicesOfLongestPath); } //Check if tolerance level is ok: if (toleranceOk == false) { fileOutput.AppendLine("\n \n WARNING: the program has been interrupted."); fileOutput.AppendLine("The tolerance level is too rough: put a lower tolerance."); listOfPathsOfPoints = null; onlyShortPaths = false; return(false); } //Check if longestPattern == true: if (longestPattern == true) { fileOutput.AppendLine("\n LongestPattern = true"); listOfPathsOfPoints = listOfPaths; onlyShortPaths = false; return(true); } //I update the list of Simple points I have not passed through yet: listOfSimplePoints_Copy.RemoveAll(point => listOfPaths[listOfPaths.Count - 1].path.Contains(point)); numOfSimple = listOfSimplePoints_Copy.Count; numOfPenultimate = listOfPenultimate.Count; } //Last searching: I go through the branches of MB satisfying some characteristics.. Part.PathCreation_Part.Functions.AddPathsFromNewCheckOfMB(matrAdjToSee, listOfOrigins, ref listOfPaths, listOfExtremePoints, listOfMBPoints, ref fileOutput, ref toleranceOk); if (toleranceOk == false) { fileOutput.AppendLine("\n \n WARNING: the program has been interrupted."); fileOutput.AppendLine("The tolerance level is too rough: put a lower tolerance."); listOfPathsOfPoints = null; onlyShortPaths = false; return(false); } //I remove the longestPath, which was not geometrically verified but its path was kept in memory //not to find it again during the process (in fact tht process, whenever it finds a new seed path //of 3 centroids, verifies if a path containing these 3 centroids already exists): //listOfPaths.RemoveAt(listOfIndicesOfLongestPath); // fileOutput.AppendLine("Numero di path prima della cancellazione dei longestPattern= " + listOfPaths.Count); listOfPaths.RemoveAll(path => listOfIndicesOfLongestPath.Contains(listOfPaths.IndexOf(path))); // fileOutput.AppendLine("Numero di path dopo della cancellazione dei longestPattern= " + listOfPaths.Count); // I order the list of MyPathOfPoints by decreasing order respect to the length of the path, // if length is the same, first line and then circumference. listOfPaths = listOfPaths.OrderByDescending(x => x.path.Count) .ThenBy(y => y.pathGeometricObject.GetType() == typeof(MyLine) ? 0 : 1) .ToList(); listOfPathsOfPoints = listOfPaths; onlyShortPaths = false; return(false); }
public static void KLFindPatternsOfComponents(List <MyRepeatedComponent> listOfComponents, List <MyVertex> listOfVertexOrigins, ref List <MyPatternOfComponents> listOfMyPattern, ref List <MyPatternOfComponents> listOfMyPatternTwo, ModelDoc2 SwModel, SldWorks swApplication, ref StringBuilder fileOutput) { //per PROVA: parto dal livello delle foglie... //I create a list of adjacency matrices at constant distance. //The constant distance is the distance between the origin of the coordinate systems //(it is computed by computing the Euclidean norm of the difference vector between // two origins). var numOfComponents = listOfComponents.Count; //var listOfVertexOrigins = listOfComponents.Select(component2 => component2.Origin).ToList(); //foreach (MyVertex origin in listOfVertexOrigins) //{ // var centroidToPrint = string.Format("{0}, {1}, {2}", origin.x, origin.y, origin.z); // //KLdebug.Print(centroidToPrint, "Centroidi.txt"); //} if (numOfComponents > 2) { //fileOutput.AppendLine("CREAZIONE MATRICI DI ADIACENZA:"); var maxPath = false; //it is TRUE if the maximum Pattern is found, FALSE otherwise. var toleranceOk = true; var listOfMyMatrAdj = Functions.CreateMatrAdj(listOfVertexOrigins, ref fileOutput); while (listOfMyMatrAdj.Count > 0 && maxPath == false && toleranceOk == true) { bool onlyShortPath; var currentMatrAdj = new MyMatrAdj(listOfMyMatrAdj[0].d, listOfMyMatrAdj[0].matr, listOfMyMatrAdj[0].nOccur); //fileOutput.AppendLine("Esamino NUOVA MatrAdj. Al momento sono rimaste " + listOfMyMatrAdj.Count + // " MatrAdj."); listOfMyMatrAdj.Remove(listOfMyMatrAdj[0]); //NOTA: forse la mia MatrAdj non deve essere rimossa ma conservata, //soprattutto nel caso in cui si presenta onlyShortPath = true //(non avrebbe senso cancellarla, ma conservarla per la ricerca di path //di 2 RE). //fileOutput.AppendLine("----> Eliminata NUOVA MatrAdj. Ora sono rimaste " + listOfMyMatrAdj.Count + // " MatrAdj."); //fileOutput.AppendLine(" "); List <MyPathOfPoints> listOfPathOfPoints; maxPath = PathCreation_Assembly.Functions.KLFindPaths_Assembly(currentMatrAdj, listOfComponents, listOfVertexOrigins, ref fileOutput, out listOfPathOfPoints, out onlyShortPath, ref toleranceOk, ref listOfMyMatrAdj, ref listOfMyPattern, ref listOfMyPatternTwo, SwModel, swApplication); //fileOutput.AppendLine(" "); //fileOutput.AppendLine("PER QUESTA MATRADJ: "); //fileOutput.AppendLine("maxPath = " + maxPath); //fileOutput.AppendLine("listOfMyPattern.Count = " + listOfMyPattern.Count); //fileOutput.AppendLine("listOfMyPatternTwo.Count = " + listOfMyPatternTwo.Count); //fileOutput.AppendLine("onlyShortPath = " + onlyShortPath); //fileOutput.AppendLine("toleranceOK = " + toleranceOk); if (toleranceOk == true) { if (listOfPathOfPoints != null) { if (maxPath == false) { if (onlyShortPath == false) { GeometryAnalysis.KLGetPatternsFromListOfPaths_Assembly(listOfPathOfPoints, listOfComponents, listOfVertexOrigins, ref listOfMyMatrAdj, ref listOfMyPattern, ref listOfMyPatternTwo, SwModel, swApplication); } else { //non faccio niente e li rimetto in gioco per } } } else { fileOutput.AppendLine(" ---> NO PATH FOUND in this adjacency matrix!"); } } else { fileOutput.AppendLine("===>> TOLLERANZA NON SUFFICIENTEMENTE PICCOLA. TERMINATO."); } } } else { if (numOfComponents == 2) { //fileOutput.AppendLine("LE COMPONENTI DI QUESTO TIPO SONO 2: "); if (Part.PartUtilities.GeometryAnalysis.IsTranslationTwoRE(listOfComponents[0].RepeatedEntity, listOfComponents[1].RepeatedEntity)) { // fileOutput.AppendLine("Le due COMPONENTI sono legate da TRASLAZIONE!"); var listOfPathOfCentroids = new List <MyPathOfPoints>(); var listOfMyMatrAdj = new List <MyMatrAdj>(); var newPatternRC = new List <MyRepeatedComponent> { listOfComponents[0], listOfComponents[1] }; if (listOfVertexOrigins.Count < 2) { swApplication.SendMsgToUser("Non ho due origini"); } var newPatternGeomObject = FunctionsLC.LinePassingThrough(listOfVertexOrigins[0], listOfVertexOrigins[1]); var newPatternType = "TRANSLATION of length 2"; var newPattern = new MyPatternOfComponents(newPatternRC, newPatternGeomObject, newPatternType); GeometryAnalysis.KLCheckAndUpdate_Assembly(newPattern, ref listOfPathOfCentroids, listOfVertexOrigins, ref listOfMyMatrAdj, ref listOfMyPattern, ref listOfMyPatternTwo); //swApplication.SendMsgToUser("Pattern da due " + listOfMyPatternTwo.Count); } else { if (Part.PartUtilities.GeometryAnalysis.IsReflectionTwoRE(listOfComponents[0].RepeatedEntity, listOfComponents[1].RepeatedEntity, swApplication)) { //fileOutput.AppendLine("Le due COMPONENTI sono legate da RIFLESSIONE!"); var listOfPathOfCentroids = new List <MyPathOfPoints>(); var listOfMyMatrAdj = new List <MyMatrAdj>(); var newPatternRC = new List <MyRepeatedComponent> { listOfComponents[0], listOfComponents[1] }; var newPatternGeomObject = FunctionsLC.LinePassingThrough(listOfVertexOrigins[0], listOfVertexOrigins[1]); var newPatternType = "REFLECTION"; var newPattern = new MyPatternOfComponents(newPatternRC, newPatternGeomObject, newPatternType); GeometryAnalysis.KLCheckAndUpdate_Assembly(newPattern, ref listOfPathOfCentroids, listOfVertexOrigins, ref listOfMyMatrAdj, ref listOfMyPattern, ref listOfMyPatternTwo); } //else //{ // fileOutput.AppendLine("PROVO CON LA ROTAZIONE:"); // double[] axisDirection; // if (GeometryAnalysis.IsRotationTwoComp180degrees_Assembly(listOfComponents[0], listOfComponents[1], // out axisDirection, SwModel, swApplication)) // { // fileOutput.AppendLine("Le due COMPONENTI sono legate da ROTAZIONE!"); // var listOfPathOfCentroids = new List<MyPathOfPoints>(); // var listOfMyMatrAdj = new List<MyMatrAdj>(); // var newPatternRC = new List<MyRepeatedComponent> // { // listOfComponents[0], // listOfComponents[1] // }; // var angle90degrees = Math.PI / 2; // var thirdVertexOnCircum = listOfVertexOrigins[0].Rotate(angle90degrees, axisDirection); // var newPatternGeomObject = FunctionsLC.CircumPassingThrough(listOfVertexOrigins[0], listOfVertexOrigins[1], thirdVertexOnCircum, ref fileOutput); // var newPatternType = "ROTATION"; // var newPattern = new MyPatternOfComponents(newPatternRC, newPatternGeomObject, newPatternType); // GeometryAnalysis.KLCheckAndUpdate_Assembly(newPattern, ref listOfPathOfCentroids, // listOfVertexOrigins, ref listOfMyMatrAdj, // ref listOfMyPattern, ref listOfMyPatternTwo); // } //} } } } }
// This function updates the list of paths adding the paths raising from the given 1st and 2nd seed set points. public static void TwoPointsGivenPaths(MyMatrAdj matrAdjToSee, int n, int startPointInd, int secondPointInd, List <MyRepeatedEntity> listOfREOnThisSurface, List <MyVertex> listCentroid, List <int> listOfExtremePoints, ref List <int> listOfSimplePoints_Copy, List <int> listOfMBPoints, ref bool longestPattern, ref List <MyPathOfPoints> listOfPaths, ref List <int> listOfPenultimate, ref List <int> listOfLast, ref StringBuilder fileOutput, ref bool toleranceOk, ref List <MyMatrAdj> listOfMatrAdj, ref List <MyGroupingSurface> listOfMyGroupingSurface, List <MyGroupingSurface> listOfInitialGroupingSurface, ref List <MyPattern> listOfOutputPattern, ref List <MyPattern> listOfOutputPatternTwo, ref List <int> listOfIndicesOfLongestPath) { if (listOfExtremePoints.Contains(secondPointInd)) //If the branch is an ExtremePoint, I treat it in a special way as I have not //the path equation yet. So I guide the 3rd point search. { //I come back, so I look what are the branches of the StartPoint List <int> BranchesSecond = matrAdjToSee.matr.GetRow(startPointInd).Find(entry => entry == 1).ToList(); BranchesSecond.Remove(secondPointInd); foreach (int branch2 in BranchesSecond) { var newMyPathOfCentroids = new MyPathOfPoints(); //if (SecondPointInd(extreme), StartPointInd(MB), branch2 don't belong to an existing path in ListOfPaths) if (listOfPaths.FindIndex(pathObject => (pathObject.path.Contains(secondPointInd) && pathObject.path.Contains(startPointInd) && pathObject.path.Contains(branch2))) == -1) { List <int> Path = new List <int>(); var pathCurve = new MyPathGeometricObject(); if (listCentroid[branch2].Lieonline(FunctionsLC.LinePassingThrough( listCentroid[startPointInd], listCentroid[secondPointInd]))) { Path = ThreePointsGivenPathsLine(matrAdjToSee, listCentroid, listOfExtremePoints, secondPointInd, startPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); // Notice that expansion will procede only in one direction } else { Path = ThreePointsGivenPathsCircum(matrAdjToSee, listCentroid, listOfExtremePoints, secondPointInd, startPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); // Notice that expansion will procede only in one direction } if (toleranceOk == false) { return; } //If I have found a complete circumference I delete the repeated centroid index: if (Path[0] == Path[Path.Count - 1]) { Path.RemoveAt(Path.Count - 1); } newMyPathOfCentroids.path = Path; newMyPathOfCentroids.pathGeometricObject = pathCurve; listOfPaths.Add(newMyPathOfCentroids); fileOutput.AppendLine("Aggiunto alla lista nuovo path: "); fileOutput.AppendLine(" -numero di baricentri:" + newMyPathOfCentroids.path.Count); if (pathCurve.GetType() == typeof(MyLine)) { fileOutput.AppendLine(" -tipo di path: retta"); fileOutput.AppendLine(""); } else { fileOutput.AppendLine(" -tipo di path: criconferenza"); fileOutput.AppendLine(""); } //If a path of length n or n-1 is found, I move up the geometrical verify to see //if the process can be stopped at this point (sufficiently satisfying result on this GS) int m = Path.Count; if (m == n || m == n - 1) { fileOutput.AppendLine("\n Trovato path che potrebbe dare un Longest Pattern: VERIFICO"); // Removing of the path from the list: //this is done because if the pattern is verified the updating phase (in particular //referred to the part of list of paths updating) will consider all the paths existing //in the list of paths (so also the current long one) and the updating would be //long and useless (we would try to compare the current path to itself). listOfPaths.RemoveAt(listOfPaths.Count - 1); if (PartUtilities.GeometryAnalysis.GetPatternsFromPath(newMyPathOfCentroids, listOfREOnThisSurface, ref listOfPaths, ref listOfMatrAdj, ref listOfMyGroupingSurface, listOfInitialGroupingSurface, ref listOfOutputPattern, ref listOfOutputPatternTwo)) { longestPattern = true; return; } else { listOfPaths.Add(newMyPathOfCentroids); // Updating of the list of Simple points not yet passed through: var ListOfPaths_copy = new List <MyPathOfPoints>(listOfPaths); listOfSimplePoints_Copy.RemoveAll(point => ListOfPaths_copy[ListOfPaths_copy.Count - 1].path.Contains(point)); UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, Path); listOfIndicesOfLongestPath.Add(listOfPaths.IndexOf(newMyPathOfCentroids)); } } else { UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, Path); } } } } else // cioè listOfMBPoints.Contains(SecondPointInd) || ListOfSimplePoints.Contains(SecondPointInd) { //trasforma in lista la selezione sull'array (SecondPointInd,:) List <int> BranchesSecond = matrAdjToSee.matr.GetRow(secondPointInd).Find(entry => entry == 1).ToList(); //levo il punto di partenza (che è sicuramente un branch) per non tornare indietro BranchesSecond.Remove(startPointInd); foreach (int branch2 in BranchesSecond) { var newMyPathOfCentroids = new MyPathOfPoints(); // if (StartPointInd, SecondPointInd, branch2 don't belong to an existing path in ListOfPaths ) if (listOfPaths.FindIndex(pathObject => (pathObject.path.Contains(startPointInd) && pathObject.path.Contains(secondPointInd) && pathObject.path.Contains(branch2))) == -1) { List <int> Path = new List <int>(); var pathCurve = new MyPathGeometricObject(); if (listCentroid[branch2].Lieonline(FunctionsLC.LinePassingThrough( listCentroid[startPointInd], listCentroid[secondPointInd]))) { Path = ThreePointsGivenPathsLine(matrAdjToSee, listCentroid, listOfExtremePoints, startPointInd, secondPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); } else { Path = ThreePointsGivenPathsCircum(matrAdjToSee, listCentroid, listOfExtremePoints, startPointInd, secondPointInd, branch2, ref fileOutput, ref toleranceOk, out pathCurve); } if (toleranceOk == false) { return; } //If I have found a complete circumference I delete the repeated centroid index: if (Path[0] == Path[Path.Count - 1]) { Path.RemoveAt(Path.Count - 1); } newMyPathOfCentroids.path = Path; newMyPathOfCentroids.pathGeometricObject = pathCurve; listOfPaths.Add(newMyPathOfCentroids); fileOutput.AppendLine("Aggiunto alla lista nuovo path: "); fileOutput.AppendLine(" -numero di baricentri:" + newMyPathOfCentroids.path.Count); if (pathCurve.GetType() == typeof(MyLine)) { fileOutput.AppendLine(" -tipo di path: retta"); } else { fileOutput.AppendLine(" -tipo di path: circonferenza"); } //If a path of length n or n-1 is found, I move up the geometrical verify to see //if the process can be stopped at this point (sufficiently satisfying result on this GS) int m = Path.Count; if (m == n || m == n - 1) { fileOutput.AppendLine("\n Trovato path che potrebbe dare un Longest Pattern: VERIFICO"); // Removing of the path from the list: listOfPaths.RemoveAt(listOfPaths.Count - 1); if (PartUtilities.GeometryAnalysis.GetPatternsFromPath(newMyPathOfCentroids, listOfREOnThisSurface, ref listOfPaths, ref listOfMatrAdj, ref listOfMyGroupingSurface, listOfInitialGroupingSurface, ref listOfOutputPattern, ref listOfOutputPatternTwo)) { longestPattern = true; return; } else { listOfPaths.Add(newMyPathOfCentroids); // Updating of the list of Simple points not yet passed through: var ListOfPaths_copy = new List <MyPathOfPoints>(listOfPaths); listOfSimplePoints_Copy.RemoveAll(point => ListOfPaths_copy[ListOfPaths_copy.Count - 1].path.Contains(point)); UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, Path); listOfIndicesOfLongestPath.Add(listOfPaths.IndexOf(newMyPathOfCentroids)); } } else { UpdateListsOfPenultimateAndLast(listOfExtremePoints, listOfMBPoints, ref listOfPenultimate, ref listOfLast, Path); } } } } }
public static void FindComposedPatterns(List <MyGroupingSurfaceForPatterns> listOfGroupingSurfaceForPatterns, out List <MyComposedPattern> listOfOutputComposedPattern, out List <MyComposedPattern> listOfOutputComposedPatternTwo, ModelDoc2 SwModel, SldWorks mySwApplication, ref StringBuilder fileOutput) { var toleranceOk = true; var listOfComposedPattern = new List <MyComposedPattern>(); var listOfComposedPatternTwo = new List <MyComposedPattern>(); //For each MyGroupingSurfaceForPatterns while (listOfGroupingSurfaceForPatterns.Count > 0 && toleranceOk) { var currentGroupingSurfaceForPatterns = new MyGroupingSurfaceForPatterns( listOfGroupingSurfaceForPatterns[0].groupingSurface, listOfGroupingSurfaceForPatterns[0].listOfPatternsLine, listOfGroupingSurfaceForPatterns[0].listOfPatternsCircum); listOfGroupingSurfaceForPatterns.RemoveAt(0); fileOutput.AppendLine(""); fileOutput.AppendLine("NUOVA SURFACE OF TYPE: " + currentGroupingSurfaceForPatterns.groupingSurface.Identity()); fileOutput.AppendLine("(Al momento sono rimaste ancora " + listOfGroupingSurfaceForPatterns.Count + " superfici (oltre questa).)"); // >>>>>>> LINEAR CASE: //first I group patterns by same length and same distance: var listOfListsOfCoherentPatternsLine = GroupFoundPatternsOfTypeLine( currentGroupingSurfaceForPatterns.listOfPatternsLine, mySwApplication); if (listOfListsOfCoherentPatternsLine.Count == 0) { } //Then I group coherent patterns in subgroups of parallel patterns: foreach (var list in listOfListsOfCoherentPatternsLine) { //Grouping in lists of parallel patterns var listOfListsOfParallelPatterns = GroupPatternsInParallel(list); var numOfListsOfParallelPatterns = listOfListsOfParallelPatterns.Count; if (list.Count == 2) { //I verify if a composed pattern with these 2 patterns has already been created //in another GS: if (ComposedPatternOfLength2AlreadyExists(listOfComposedPatternTwo, list) == false) { //if a composed pattern does not exist yet AND //the 2 patterns are not parallel, I verify if it is REFLECTION: if (numOfListsOfParallelPatterns == 0) { if (IsReflectionTwoPatterns(list[0], list[1])) { var typeOfNewComposedPattern = "Composed REFLECTION of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, list); } } else //if a composed pattern does not exist yet AND //the 2 patterns are parallel, I verify if it is TRANSLARION: { if (IsTranslationTwoPatterns(list[0], list[1])) { var typeOfNewComposedPattern = "Composed TRANSLATION of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, list); } else { if (IsReflectionTwoPatterns(list[0], list[1])) { var typeOfNewComposedPattern = "Composed REFLECTION of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, list); } } } } } else { foreach (var listOfParallelPatterns in listOfListsOfParallelPatterns) { if (listOfParallelPatterns.Count == 2) { //I verify if a composed pattern with these 2 patterns has already been created //in another GS: if (ComposedPatternOfLength2AlreadyExists(listOfComposedPatternTwo, list)) { } else { if (IsTranslationTwoPatterns(listOfParallelPatterns[0], listOfParallelPatterns[1])) { var typeOfNewComposedPattern = "Composed TRANSLATION of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, listOfParallelPatterns); } else { if (IsReflectionTwoPatterns(list[0], list[1])) { var typeOfNewComposedPattern = "Composed REFLECTION of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, list); } } } } else //(listOfParallelPatterns.Count > 2) { var listOfPatternCentroids = listOfParallelPatterns.Select(pattern => pattern.patternCentroid).ToList(); fileOutput.AppendLine(""); fileOutput.AppendLine(" >>>> CREATION OF ADJECENCY MATRICES FOR COMPOSED PATTERNS:"); var listOfMyMatrAdj = Functions.CreateMatrAdj(listOfPatternCentroids, ref fileOutput); var maxPath = false; //it is TRUE if the maximum Pattern is found, FALSE otherwise. while (listOfMyMatrAdj.Count > 0 && maxPath == false && toleranceOk) { var currentMatrAdj = new MyMatrAdj(listOfMyMatrAdj[0].d, listOfMyMatrAdj[0].matr, listOfMyMatrAdj[0].nOccur); listOfMyMatrAdj.Remove(listOfMyMatrAdj[0]); //NOTA: forse la mia MatrAdj non deve essere rimossa ma conservata, //soprattutto nel caso in cui si presenta onlyShortPath = true //(non avrebbe senso cancellarla, ma conservarla per la ricerca di path //di 2 RE). List <MyPathOfPoints> listOfPathsOfCentroids; bool onlyShortPaths; maxPath = PathCreation_Part_ComposedPatterns.Functions.FindPaths_ComposedPatterns(currentMatrAdj, listOfParallelPatterns, ref fileOutput, out listOfPathsOfCentroids, out onlyShortPaths, ref toleranceOk, ref listOfMyMatrAdj, ref listOfGroupingSurfaceForPatterns, ref listOfComposedPattern, ref listOfComposedPatternTwo, mySwApplication); //fileOutput.AppendLine("listOfPathOfCentroids.Count = " + listOfPathOfCentroids.Count, nameFile); if (toleranceOk) { if (listOfPathsOfCentroids != null) { if (maxPath == false) { if (onlyShortPaths == false) { GetComposedPatternsFromListOfPathsLine(listOfPathsOfCentroids, listOfParallelPatterns, ref listOfMyMatrAdj, ref listOfGroupingSurfaceForPatterns, ref listOfComposedPattern, ref listOfComposedPatternTwo, mySwApplication, ref fileOutput); } else { //non faccio niente e li rimetto in gioco per } } } } } } } //Now coherent linear patterns that have not been set in a composed pattern yet //are examined to see if they consitute any rotation composed pattern: list.RemoveAll( pattern => listOfComposedPattern.FindIndex( composedPattern => composedPattern.listOfMyPattern.FindIndex( patternInComposedPattern => patternInComposedPattern.idMyPattern == pattern.idMyPattern) != -1) != -1); if (list.Count != 0) { if (list.Count == 2) { // >>> POSSIBLE REFLECTION CAN EXIST //I verify if a composed pattern with these 2 patterns has already been created //in another GS: if (ComposedPatternOfLength2AlreadyExists(listOfComposedPatternTwo, list)) { } else { if (IsReflectionTwoPatterns(list[0], list[1])) { var typeOfNewComposedPattern = "Composed REFLECTION of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, list); } } } else { var listOfPatternCentroids1 = list.Select(pattern => pattern.patternCentroid).ToList(); fileOutput.AppendLine(""); fileOutput.AppendLine(" >>>> CREATION OF ADJECENCY MATRICES FOR COMPOSED PATTERNS:"); var listOfMyMatrAdj1 = Functions.CreateMatrAdj(listOfPatternCentroids1, ref fileOutput); var maxPath = false; //it is TRUE if the maximum Pattern is found, FALSE otherwise. while (listOfMyMatrAdj1.Count > 0 && maxPath == false && toleranceOk) { var currentMatrAdj = new MyMatrAdj(listOfMyMatrAdj1[0].d, listOfMyMatrAdj1[0].matr, listOfMyMatrAdj1[0].nOccur); listOfMyMatrAdj1.Remove(listOfMyMatrAdj1[0]); //NOTA: forse la mia MatrAdj non deve essere rimossa ma conservata, //soprattutto nel caso in cui si presenta onlyShortPath = true //(non avrebbe senso cancellarla, ma conservarla per la ricerca di path //di 2 RE). List <MyPathOfPoints> listOfPathsOfCentroids1; bool onlyShortPaths1; var maxPath1 = PathCreation_Part_ComposedPatterns.Functions.FindPaths_ComposedPatterns(currentMatrAdj, list, ref fileOutput, out listOfPathsOfCentroids1, out onlyShortPaths1, ref toleranceOk, ref listOfMyMatrAdj1, ref listOfGroupingSurfaceForPatterns, ref listOfComposedPattern, ref listOfComposedPatternTwo, mySwApplication); if (toleranceOk) { if (listOfPathsOfCentroids1 != null) { //I ignore every linear path (I look for composed rotational patterns now): var listOfCircularPaths = listOfPathsOfCentroids1.FindAll( path => path.pathGeometricObject.GetType() == typeof(MyCircumForPath)) .ToList(); if (maxPath1 == false) { if (onlyShortPaths1 == false) { GetComposedPatternsFromListOfPathsLine(listOfCircularPaths, list, ref listOfMyMatrAdj1, ref listOfGroupingSurfaceForPatterns, ref listOfComposedPattern, ref listOfComposedPatternTwo, mySwApplication, ref fileOutput); } else { //non faccio niente e li rimetto in gioco per } } } } } } } } } // >>>>>>> CIRCULAR CASE: #region da rivedere //first I group patterns by same length and same distance: var listOfListsOfCoherentPatternsCircum = GroupFoundPatternsOfTypeCircum( currentGroupingSurfaceForPatterns.listOfPatternsCircum, mySwApplication); //Then I group coherent patterns in subgroups of patterns: foreach (var list in listOfListsOfCoherentPatternsCircum) { var listOfListsOfPatternsWithSameCenterAndPlane = GroupPatternsWithSameCenterPlane(list); var numOfListsOfParallelPatterns = listOfListsOfPatternsWithSameCenterAndPlane.Count; //Grouping in lists of parallel patterns foreach (var listOfPatternsWithSameCenterAndPlane in listOfListsOfPatternsWithSameCenterAndPlane) { if (listOfPatternsWithSameCenterAndPlane.Count == 2) { if (IsTranslationTwoPatterns(listOfPatternsWithSameCenterAndPlane[0], listOfPatternsWithSameCenterAndPlane[1])) { var typeOfNewComposedPattern = "Composed ROTATIONAL (same center) of length 2"; BuildNewComposedPatternOfLength2(fileOutput, typeOfNewComposedPattern, ref listOfComposedPattern, ref listOfComposedPatternTwo, ref listOfGroupingSurfaceForPatterns, listOfPatternsWithSameCenterAndPlane); } } else //listOfPatternsWithSameCenterAndPlane.Count > 2 { // var listOfPatternCentroids = // listOfPatternsWithSameCenterAndPlane.Select(pattern => pattern.patternCentroid).ToList(); // KLdebug.Print("", nameFile); // KLdebug.Print(" >>>> CREATION OF ADJECENCY MATRICES FOR COMPOSED PATTERNS:", nameFile); // var listOfMyMatrAdj = Functions.CreateMatrAdj(listOfPatternCentroids, ref fileOutput); // var indOfMatr = 0; // List<MyPathOfPoints> listOfPathsOfCentroids; // bool onlyShortPaths; // ////////////// // var maxPath = Functions.FindPaths_ComposedPatterns(listOfMyMatrAdj[indOfMatr], listOfPatternsWithSameCenterAndPlane, // ref fileOutput, out listOfPathsOfCentroids, out onlyShortPaths, ref toleranceOk, ref listOfMyMatrAdj, // ref listOfGroupingSurfaceForPatterns, ref listOfComposedPattern, ref listOfComposedPatternTwo); // if (toleranceOk) // { // if (maxPath == false) // { // if (onlyShortPaths == false) // { // GetComposedPatternsFromListOfPathsLine(listOfPathsOfCentroids, // listOfPatternsWithSameCenterAndPlane, // ref listOfMyMatrAdj, ref listOfGroupingSurfaceForPatterns, // ref listOfComposedPattern, ref listOfComposedPatternTwo); // } // else // { // //non faccio niente e li rimetto in gioco per // } // } // } // else // { // KLdebug.Print("===>> TOLLERANZA NON SUFFICIENTEMENTE PICCOLA. TERMINATO.", nameFile); // } } } } } #endregion listOfOutputComposedPattern = listOfComposedPattern; listOfOutputComposedPatternTwo = listOfComposedPatternTwo; }
//Crea il massimo path CIRCONFERENZA a partire dai 3 punti dati public static List <int> ThreePointsGivenPathsCircum(MyMatrAdj MatrAdjToSee, List <MyVertex> ListCentroid, List <int> ListOfExtremePoints, int Point1, int Point2, int Point3, ref StringBuilder fileOutput, ref bool ToleranceOk, out MyPathGeometricObject pathCurve, ModelDoc2 swModel = null, SldWorks swApplication = null) { List <int> Path = new List <int>(); Path.Add(Point1); Path.Add(Point2); Path.Add(Point3); MyCircumForPath CircumPath = FunctionsLC.CircumPassingThrough( ListCentroid[Point1], ListCentroid[Point2], ListCentroid[Point3], ref fileOutput, swModel, swApplication); //procedo nella direzione Point2-Point3 fileOutput.AppendLine("Point3: " + Point3); List <int> BranchesThird = MatrAdjToSee.matr.GetRow(Point3).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Point2); //foreach (int ind in BranchesThird) //{ // fileOutput.AppendLine("\n branch del 3° punto " + Point3 + ": " + ind); //} int Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)); while (Next != -1 && BranchesThird[Next] != Point1) // mi devo fermare anche quando completo la circonferenza, se non va all'infinito { // Check if the tolerance is too rough int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)).Count; if (NumOfFound == 1) { //List<int> listafind = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)); //foreach (int ind in listafind) //{ // fileOutput.AppendLine("Branch candidato a proseguire il path (dovrebbe essere solo uno!): " + ind); //} //fileOutput.AppendLine("Next: " + Next); int NextInd = BranchesThird[Next]; //fileOutput.AppendLine("Nextind: " + NextInd); BranchesThird.Clear(); BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Path.Last()); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in coda), perché se no tornerei indietro Path.Add(NextInd); //aggiungo in coda al path Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)); } else { fileOutput.AppendLine("NumOfFound > 1 !!!!"); //End the execution in the higher levels ToleranceOk = false; pathCurve = null; return(Path); } } #region Check if I can invert the direction of expansion on not //se non ho ancora completato il giro (Next=-1) e Point1 non era un Extreme point, inverto la direzione procedendo verso Point2-Point1 if (Next == -1) { if (!(ListOfExtremePoints.Contains(Point1))) { fileOutput.AppendLine("non ho ancora completato il giro"); BranchesThird.Clear(); BranchesThird = MatrAdjToSee.matr.GetRow(Point1).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Point2); Next = BranchesThird.FindIndex(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)); while (Next != -1) // qui sono sicura che che non completerò mai la crf, se no l'avrebbe già completata nell'altro while { // Check if the tolerance is too rough int NumOfFound = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)) .Count; if (NumOfFound == 1) { //List<int> listafind = BranchesThird.FindAll(ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)); //foreach (int ind in listafind) //{ // fileOutput.AppendLine("Branch candidato a proseguire il path (dovrebbe essere solo uno!): " + ind); //} //fileOutput.AppendLine("Next: " + Next); int NextInd = BranchesThird[Next]; //fileOutput.AppendLine("Nextind: " + NextInd); Console.ReadLine(); BranchesThird.Clear(); BranchesThird = MatrAdjToSee.matr.GetRow(NextInd).Find(entry => entry == 1).ToList(); //cerco tra questi BranchesThird.Remove(Path[0]); //rimuovo dai branch trovati l'ultimo elemento che avevo aggiunto al path (in testa), perché se no tornerei indietro Path.Insert(0, NextInd); //aggiungo in testa al path Next = BranchesThird.FindIndex( ind_branch => ListCentroid[ind_branch].Lieoncircum(CircumPath)); } else { fileOutput.AppendLine("NumOfFound > 1 !!!! ERRORE. "); //End the execution in the higher levels ToleranceOk = false; pathCurve = null; return(Path); } } } } else //si è usciti dal 1° while perché BranchesThird[Next] == Point1, cioè ho completato il giro { Path.Add(BranchesThird[Next]); //aggiungo Point1 al Path (faccio un ciclo chiuso) } #endregion fileOutput.AppendLine("\n Nuovo path circonferenza:"); foreach (int ind in Path) { fileOutput.AppendLine(" - " + ind); } pathCurve = CircumPath; if (CircumPath != null) { return(Path); } Path.Clear(); return(Path); } //fine ThreePointsGivenPathsCircum
//PRIMA DI USARE QUESTO METODO RICORDARSI DI ELIMINARE LA CURRENTgROUPINGSURFACE DALLA LISTA!!!! public static void FindPatternsInGS(MyGroupingSurface currentGroupingSurface, ref StringBuilder fileOutput, ref List <MyPattern> listOfMyPattern, ref List <MyGroupingSurface> listOfMyGroupingSurface, ref List <MyPattern> listOfMyPatternTwo, ref bool toleranceOK, List <MyGroupingSurface> listOfInitialGroupingSurface) { var ListOfREOnThisSurface = currentGroupingSurface.listOfREOfGS.Select(myRepeatedEntity => myRepeatedEntity).ToList(); var listOfCentroidsThisGS = currentGroupingSurface.listOfREOfGS.Select(myRepeatedEntity => myRepeatedEntity.centroid).ToList(); var numOfCentroidsOnThisGS = listOfCentroidsThisGS.Count; var maxPath = false; //it is TRUE if the maximum Pattern is found, FALSE otherwise. if (numOfCentroidsOnThisGS > 2) { List <MyMatrAdj> listOfMyMatrAdj = Functions.CreateMatrAdj(listOfCentroidsThisGS, ref fileOutput); while (listOfMyMatrAdj.Count > 0 && maxPath == false && toleranceOK == true) { bool onlyShortPath; var currentMatrAdj = new MyMatrAdj(listOfMyMatrAdj[0].d, listOfMyMatrAdj[0].matr, listOfMyMatrAdj[0].nOccur); listOfMyMatrAdj.Remove(listOfMyMatrAdj[0]); //NOTA: forse la mia MatrAdj non deve essere rimossa ma conservata, //soprattutto nel caso in cui si presenta onlyShortPath = true //(non avrebbe senso cancellarla, ma conservarla per la ricerca di path //di 2 RE). fileOutput.AppendLine("----> Considero NUOVA MatrAdj. Sono rimaste ancora " + listOfMyMatrAdj.Count + " MatrAdj da controllare."); fileOutput.AppendLine(" "); List <MyPathOfPoints> listOfPathOfCentroids; maxPath = Functions.FindPaths(currentMatrAdj, ListOfREOnThisSurface, ref fileOutput, out listOfPathOfCentroids, out onlyShortPath, ref toleranceOK, ref listOfMyMatrAdj, ref listOfMyGroupingSurface, listOfInitialGroupingSurface, ref listOfMyPattern, ref listOfMyPatternTwo); fileOutput.AppendLine(" "); fileOutput.AppendLine("PER QUESTA MATRADJ prima della ricerca 'ufficiale' di pattern': "); fileOutput.AppendLine("maxPath = " + maxPath); fileOutput.AppendLine("listOfMyPattern.Count = " + listOfMyPattern.Count); fileOutput.AppendLine("listOfMyPatternTwo.Count = " + listOfMyPatternTwo.Count); fileOutput.AppendLine("onlyShortPath = " + onlyShortPath); fileOutput.AppendLine("toleranceOK = " + toleranceOK); //fileOutput.AppendLine("listOfPathOfCentroids.Count = " + listOfPathOfCentroids.Count); if (toleranceOK == true) { if (listOfPathOfCentroids != null) { if (maxPath == false) { if (onlyShortPath == false) { GetPatternsFromListOfPaths(listOfPathOfCentroids, ListOfREOnThisSurface, ref listOfMyMatrAdj, ref listOfMyGroupingSurface, listOfInitialGroupingSurface, ref listOfMyPattern, ref listOfMyPatternTwo); } else { //non faccio niente e li rimetto in gioco per } } } else { fileOutput.AppendLine(" ---> NO PATH FOUND in this adjacency matrix!"); } } else { fileOutput.AppendLine("===>> TOLLERANZA NON SUFFICIENTEMENTE PICCOLA. TERMINATO."); return; } } } else { //numOfCentroidsOnThisGS = 2 if (numOfCentroidsOnThisGS == 2) { fileOutput.AppendLine("Su QUESTA GS ci sono solo 2 RE: "); if (IsTranslationTwoRE(ListOfREOnThisSurface[0], ListOfREOnThisSurface[1])) { fileOutput.AppendLine("Le due RE sono legate da TRASLAZIONE!"); var listOfPathOfCentroids = new List <MyPathOfPoints>(); var listOfMyMatrAdj = new List <MyMatrAdj>(); var newPatternRE = new List <MyRepeatedEntity>(); newPatternRE.Add(ListOfREOnThisSurface[0]); newPatternRE.Add(ListOfREOnThisSurface[1]); var newPatternGeomObject = FunctionsLC.LinePassingThrough(listOfCentroidsThisGS[0], listOfCentroidsThisGS[1]); var newPatternType = "TRANSLATION of length 2"; var listOfGroupingSurfaceForThisPattern = findGroupingSurfacesForThisPattern(listOfInitialGroupingSurface, newPatternRE, numOfCentroidsOnThisGS); var newPattern = new MyPattern(newPatternRE, newPatternGeomObject, newPatternType, listOfGroupingSurfaceForThisPattern); CheckAndUpdate(newPattern, ref listOfPathOfCentroids, ListOfREOnThisSurface, ref listOfMyMatrAdj, ref listOfMyGroupingSurface, ref listOfMyPattern, ref listOfMyPatternTwo); } else { if (IsReflectionTwoRE(ListOfREOnThisSurface[0], ListOfREOnThisSurface[1], null)) { fileOutput.AppendLine("Le due RE sono legate da RIFLESSIONE!"); var listOfPathOfCentroids = new List <MyPathOfPoints>(); var listOfMyMatrAdj = new List <MyMatrAdj>(); var newPatternRE = new List <MyRepeatedEntity>(); newPatternRE.Add(ListOfREOnThisSurface[0]); newPatternRE.Add(ListOfREOnThisSurface[1]); var newPatternGeomObject = FunctionsLC.LinePassingThrough(listOfCentroidsThisGS[0], listOfCentroidsThisGS[1]); var newPatternType = "REFLECTION"; var listOfGroupingSurfaceForThisPattern = findGroupingSurfacesForThisPattern(listOfInitialGroupingSurface, newPatternRE, numOfCentroidsOnThisGS); var newPattern = new MyPattern(newPatternRE, newPatternGeomObject, newPatternType, listOfGroupingSurfaceForThisPattern); CheckAndUpdate(newPattern, ref listOfPathOfCentroids, ListOfREOnThisSurface, ref listOfMyMatrAdj, ref listOfMyGroupingSurface, ref listOfMyPattern, ref listOfMyPatternTwo); } } } } }