/// <summary> /// Sets random hyperplane which has points in the given region /// </summary> /// <param name="region"></param> /// <param name="hplane"></param> public static void SetRandPlane(Hyperrect region, ref Hyperplane hplane) { hplane.Point.SetRandom(region); hplane.Normal.SetRandom(-1.0, 1.0); hplane.Normal.Multiply(1.0 / Math.Sqrt(hplane.Normal.SquaredNorm())); hplane.Distance = hplane.Point.DotProduct(hplane.Normal); }
private static IEnumerable GetNDimensionPoints() { PlanePoint[] points = new PlanePoint[] { new PlanePoint(new double[] { 1, 1, 0 }), new PlanePoint(new double[] { 5, 1, 0 }), new PlanePoint(new double[] { 1, 5, 0 }), new PlanePoint(new double[] { 5, 5, 0 }), new PlanePoint(new double[] { 1, 1, 5 }), new PlanePoint(new double[] { 5, 1, 5 }), new PlanePoint(new double[] { 1, 5, 5 }), new PlanePoint(new double[] { 5, 5, 5 }), new PlanePoint(new double[] { 3, 3, 3 }), }; Vector v1 = new Vector(new double[] { 0, 0, -1 }); Vector v2 = new Vector(new double[] { 0, -1, 0 }); Vector v3 = new Vector(new double[] { -1, 0, 0 }); Hyperplane[] expect = new Hyperplane[] { new Hyperplane(points[0], v1), new Hyperplane(points[0], v2), new Hyperplane(points[0], v3), }; yield return(new TestCaseData(points).SetName("{m}_3dPoints")); }
public void Initialization_UsingHyperplane() { Hyperplane plane1 = new Hyperplane(new PlanePoint(new double[] { 0, 0 }), new Vector(new double[] { 1, 1 })); Face face = new Face(plane1); face.Hyperplane.Should().Equals(plane1); }
public CuratorConvexHull(Hyperplane firstPlane) { _faces = new List <IFace>(); _processedPlanes = new Dictionary <Hyperplane, IFace>(new HyperplaneComparer()); _dim = firstPlane.Dimension; AddNewFace(new Face(firstPlane)); }
private static IEnumerable <TestCaseData> GetDataForConvertPoint() { PlanePoint mainPoint = new PlanePoint(new double[] { 1, 1, 2 }); Vector normal = new Vector(new double[] { 1, 0, 0 }); Vector[] basis = new[] { new Vector(new double[] { 1, 0, 0 }), new Vector(new double[] { 0, 1, 0 }), }; Hyperplane hyperplane = new Hyperplane(mainPoint, normal); hyperplane.Basis = basis; Point point = new Point(new double[] { 2, 2, 2 }); Point expect = new Point(new double[] { 1, 1 }); yield return(new TestCaseData(hyperplane, point).Returns(expect)); mainPoint = new PlanePoint(new double[] { 2, 2, 4 }); normal = new Vector(new double[] { 2, 0, 2 }); basis = new[] { new Vector(new double[] { -2, 0, 2 }), new Vector(new double[] { 0, 1, 0 }), }; hyperplane = new Hyperplane(mainPoint, normal); hyperplane.Basis = basis; point = new Point(new double[] { 2, 5, 4 }); expect = new Point(new double[] { 0, 3 }); yield return(new TestCaseData(hyperplane, point).Returns(expect)); }
public void FindFirstPlane_Simplex_ReturnHyperplane(Point[] points, Hyperplane[] expected) { PlaneFinder planeFinder = new PlaneFinder(); Hyperplane result = planeFinder.FindFirstPlane(points.ToPlanePoint()); expected.Should().Contain(result); }
public void Angle_SamePlane_ReturnAngle() { PlanePoint p1 = new PlanePoint(3); Vector n1 = new Vector(new double[] { 1, 0, 0 }); Hyperplane h1 = new Hyperplane(p1, n1); const double expect = 0; double result = h1.Angle(h1); Assert.AreEqual(expect, result, Tools.Eps); }
public void AddNewPlane(Hyperplane plane, IFace parentFace) { if (_processedPlanes.TryGetValue(plane, out IFace face)) { face.AdjacentCells.Add(parentFace); return; } Face newFace = new Face(plane); newFace.AdjacentCells.Add(parentFace); AddNewFace(newFace); }
public void ReorientNormal_WhenCall_ChangeOrientationNormal() { PlanePoint p1 = new PlanePoint(3); Vector n1 = new Vector(new double[] { 1, 1, 1 }); Hyperplane h1 = new Hyperplane(p1, n1); Vector n2 = new Vector(new double[] { -1, -1, -1 }); Hyperplane h2 = new Hyperplane(p1, n2); h1.ReorientNormal(); Assert.AreEqual(h2.Normal, h1.Normal); }
public void Side_PointOfPlane_ReturnPosition() { PlanePoint p1 = new PlanePoint(3); Vector n1 = new Vector(new double[] { 1, 0, 0 }); Hyperplane h1 = new Hyperplane(p1, n1); Point p2 = new Point(new double[] { 0, 4, 4 }); const int expect = 0; int result = h1.Side(p2); Assert.AreEqual(expect, result); }
public void Equals_UnequalPlane_ReturnFalse() { PlanePoint p1 = new PlanePoint(new double[] { 1, 7, 0 }); Vector n1 = new Vector(new double[] { 1, -1, 0 }); Hyperplane h1 = new Hyperplane(p1, n1); PlanePoint p2 = new PlanePoint(new double[] { -1, 3, 0 }); Vector n2 = new Vector(new double[] { -4, 2, 0 }); Hyperplane h2 = new Hyperplane(p2, n2); bool result = h1.Equals(h2); Assert.AreEqual(false, result); }
public void Angle_WhenCall_ReturnAngle() { PlanePoint p1 = new PlanePoint(3); Vector n1 = new Vector(new double[] { 1, 0, 0 }); Vector n2 = new Vector(new double[] { 0, 1, 0 }); Hyperplane h1 = new Hyperplane(p1, n1); Hyperplane h2 = new Hyperplane(p1, n2); const double expect = Math.PI / 2; double result = h1.Angle(h2); Assert.AreEqual(expect, result, Tools.Eps); }
public void GetHashCode_WhenCall_SameValue() { PlanePoint p1 = new PlanePoint(new double[] { 1, 7, 0 }); Vector n1 = new Vector(new double[] { -2, 1, 0 }); Hyperplane h1 = new Hyperplane(p1, n1); PlanePoint p2 = new PlanePoint(new double[] { -1, 3, 0 }); Vector n2 = new Vector(new double[] { -4, 2, 0 }); Hyperplane h2 = new Hyperplane(p2, n2); int result1 = h1.GetHashCode(); int result2 = h2.GetHashCode(); Assert.AreEqual(result1, result2); }
public void Create_2dPoints_ReturnHyperplane() { PlanePoint[] points = new PlanePoint[] { new PlanePoint(new double[] { 0, 0 }), new PlanePoint(new double[] { 0, 4 }) }; Vector normal = new Vector(new double[] { -1, 0 }); Hyperplane h2 = new Hyperplane(points[0], normal); Hyperplane h = Hyperplane.Create(points); Assert.AreEqual(h2, h); }
public void Create_2dPoints_ReturnHyperplane2() { PlanePoint[] points = new PlanePoint[] { new PlanePoint(new double[] { 2, 1 }), new PlanePoint(new double[] { 1, 1 }) }; Hyperplane h = Hyperplane.Create(points); double y = h.Normal[0] * (-1); double t = 9 / y; Assert.IsTrue(true); }
public void ConvertVector_ReturnPlanePoint() { PlanePoint mainPoint = new PlanePoint(new double[] { 2, 2, 4 }); Vector normal = new Vector(new double[] { 1, 0, 1 }); Vector[] basis = new[] { new Vector(new double[] { -1, 0, 1 }), new Vector(new double[] { 0, 1, 0 }), }; Hyperplane hyperplane = new Hyperplane(mainPoint, normal); hyperplane.Basis = basis; Vector vector = new Vector(new double[] { 2, 3 }); Vector expect = new Vector(new double[] { -2, 3, 2 }); Vector actual = hyperplane.ConvertVector(vector); actual.Should().Be(expect); }
public IConvexHull FindConvexHull(IList <PlanePoint> points) { int dim = points[0].Dim; if (dim == 2) { return(new ConvexHull2d(points)); } ConvexHull convexHull = new ConvexHull(dim); PlanePoint[] planePoints = new PlanePoint[points.Count - 1]; for (int i = 0; i < points.Count; i++) { int k = 0; for (int j = 0; j < points.Count; j++) { if (j == i) { continue; } planePoints[k++] = points[j]; } Hyperplane hyperplane = Hyperplane.Create(planePoints); List <PlanePoint> convertPoints = planePoints.Select((point => hyperplane.ConvertPoint(point))).ToList(); Face newFace = new Face(hyperplane); newFace.ConvexHull = FindConvexHull(convertPoints); foreach (ICell f in newFace.ConvexHull.Cells) { newFace.AdjacentCells.Add((IFace)f); ((IFace)f).AdjacentCells.Add(newFace); } convexHull.AddInnerCell(newFace); } return(convexHull); }
public void Test_WhenCall_ReturnIndexVector() { PlanePoint[] points = new PlanePoint[] { new PlanePoint(new double[] { 5, 1, 1, 1, 1 }), new PlanePoint(new double[] { 1, 5, 1, 1, 1 }), new PlanePoint(new double[] { 5, 5, 1, 1, 1 }), new PlanePoint(new double[] { 1, 1, 5, 1, 1 }), new PlanePoint(new double[] { 5, 1, 5, 1, 1 }), new PlanePoint(new double[] { 1, 5, 5, 1, 1 }), new PlanePoint(new double[] { 5, 5, 5, 1, 1 }), new PlanePoint(new double[] { 1, 1, 1, 5, 1 }), new PlanePoint(new double[] { 5, 1, 1, 5, 1 }), new PlanePoint(new double[] { 1, 5, 1, 5, 1 }), new PlanePoint(new double[] { 5, 5, 1, 5, 1 }), new PlanePoint(new double[] { 1, 1, 5, 5, 1 }), new PlanePoint(new double[] { 1, 1, 1, 1, 1 }), new PlanePoint(new double[] { 5, 1, 5, 5, 1 }), new PlanePoint(new double[] { 1, 5, 5, 5, 1 }), new PlanePoint(new double[] { 5, 5, 5, 5, 1 }), new PlanePoint(new double[] { 1, 1, 1, 1, 5 }), new PlanePoint(new double[] { 5, 1, 1, 1, 5 }), new PlanePoint(new double[] { 1, 5, 1, 1, 5 }), new PlanePoint(new double[] { 5, 5, 1, 1, 5 }), new PlanePoint(new double[] { 1, 1, 5, 1, 5 }), new PlanePoint(new double[] { 5, 1, 5, 1, 5 }), new PlanePoint(new double[] { 1, 5, 5, 1, 5 }), new PlanePoint(new double[] { 5, 5, 5, 1, 5 }), new PlanePoint(new double[] { 1, 1, 1, 5, 5 }), new PlanePoint(new double[] { 5, 1, 1, 5, 5 }), new PlanePoint(new double[] { 1, 5, 1, 5, 5 }), new PlanePoint(new double[] { 5, 5, 1, 5, 5 }), new PlanePoint(new double[] { 1, 1, 5, 5, 5 }), new PlanePoint(new double[] { 5, 1, 5, 5, 5 }), new PlanePoint(new double[] { 1, 5, 5, 5, 5 }), new PlanePoint(new double[] { 5, 5, 5, 5, 5 }), }; //PlaneFinder planeFinder = new PlaneFinder(); //Hyperplane result = planeFinder.FindFirstPlane(points.ToPlanePoint()); Stopwatch sp = new Stopwatch(); // sp.Start(); // // sp.Stop(); // // double first = sp.ElapsedMilliseconds; sp.Reset(); sp.Start(); PlaneFinder planeFinder1 = new PlaneFinder(); Hyperplane result1 = planeFinder1.FindFirstPlane(points.ToPlanePoint()); sp.Stop(); double sec = sp.ElapsedMilliseconds; sp.Reset(); sp.Start(); PlaneFinder planeFinder2 = new PlaneFinder(); Hyperplane result2 = planeFinder1.FindFirstPlane(points.ToPlanePoint()); sp.Stop(); double sec2 = sp.ElapsedMilliseconds; Assert.AreEqual(points[2], result1); }
private IConvexHull FindConvexHullNd(IList <PlanePoint> points) { int dim = points[0].Dim; Hyperplane firstPlane = _planeFinder.FindFirstPlane(points); CuratorConvexHull curator = new CuratorConvexHull(firstPlane); foreach (IFace currentFace in curator.GetFaces()) { bool[] pointsMap = new bool[points.Count]; List <PlanePoint> planePoints = new List <PlanePoint>(); for (int i = 0; i < points.Count; i++) { if (!currentFace.Hyperplane.IsPointInPlane(points[i])) { continue; } pointsMap[i] = true; planePoints.Add(currentFace.Hyperplane.ConvertPoint(points[i])); } currentFace.ConvexHull = FindConvexHull(planePoints); if (planePoints.Count == points.Count) { return(currentFace.ConvexHull); } foreach (ICell edge in currentFace.ConvexHull.Cells) { Hyperplane facePlane = currentFace.Hyperplane; Vector innerVector = facePlane.ConvertVector(-edge.Hyperplane.Normal); PlanePoint mainPoint = edge.Hyperplane.MainPoint.GetPoint(dim); Vector[] edgeBasis = edge.Hyperplane.Basis.Select(facePlane.ConvertVector).ToArray(); double minCos = double.MaxValue; Vector nextVector = default; for (int i = 0; i < points.Count; i++) { if (pointsMap[i]) { continue; } Vector newVector = Point.ToVector(mainPoint, points[i]); newVector = edgeBasis.GetOrthonormalVector(newVector); if (Tools.EQ(newVector.Length)) { continue; } double newCos = newVector.Cos(innerVector); if (Tools.GT(newCos, minCos)) { continue; } minCos = newCos; nextVector = newVector; } Vector[] newFaceBasis = CreateFaceBasis(edgeBasis, nextVector); Hyperplane nextHyperplane = Hyperplane.Create(mainPoint, newFaceBasis); nextHyperplane.SetOrientationNormal(planePoints); curator.AddNewPlane(nextHyperplane, currentFace); } } return(curator.GetConvexHull()); }
private static IEnumerable SetPoints() { // PlanePoint[] points1 = new PlanePoint[] { // new PlanePoint(new double[]{1, 1, 1, 1}), // new PlanePoint(new double[]{5, 1, 1, 1}), // new PlanePoint(new double[]{1, 5, 1, 1}), // new PlanePoint(new double[]{5, 5, 1,1}), // new PlanePoint(new double[]{1, 1, 5,1}), // new PlanePoint(new double[]{5, 1, 5,1}), // new PlanePoint(new double[]{1, 5, 5,1}), // new PlanePoint(new double[]{5, 5, 5,1}), // new PlanePoint(new double[]{1, 1, 1, 5}), // new PlanePoint(new double[]{5, 1, 1, 5}), // new PlanePoint(new double[]{1, 5, 1, 5}), // new PlanePoint(new double[]{5, 5, 1,5}), // new PlanePoint(new double[]{1, 1, 5,5}), // new PlanePoint(new double[]{5, 1, 5,5}), // new PlanePoint(new double[]{1, 5, 5,5}), // new PlanePoint(new double[]{5, 5, 5,5}), // // }; // // Vector v11 = new Vector(new double[] { -1, 0 }); // Vector v21 = new Vector(new double[] { 0, -1 }); // Hyperplane[] expect1 = new Hyperplane[] // { // new Hyperplane(points1[3], v11), // new Hyperplane(points1[3], v21), // }; // // yield return new object[] { points1, expect1 }; PlanePoint[] points = new PlanePoint[] { new PlanePoint(new double[] { 4, 0 }), new PlanePoint(new double[] { 0, 4 }), new PlanePoint(new double[] { 4, 4 }), new PlanePoint(new double[] { 0, 0 }), new PlanePoint(new double[] { 0.5, 0.5 }), new PlanePoint(new double[] { 1, 1 }), }; Vector v1 = new Vector(new double[] { -1, 0 }); Vector v2 = new Vector(new double[] { 0, -1 }); Hyperplane[] expect = new Hyperplane[] { new Hyperplane(points[3], v1), new Hyperplane(points[3], v2), }; yield return(new object[] { points, expect }); points = new PlanePoint[] { new PlanePoint(new double[] { 4, 0, 0 }), new PlanePoint(new double[] { 0, 4, 0 }), new PlanePoint(new double[] { 0, 0, 4 }), new PlanePoint(new double[] { 0, 0, 0 }), new PlanePoint(new double[] { 0.5, 0.5, 0.5 }), new PlanePoint(new double[] { 1, 1, 1 }), new PlanePoint(new double[] { 1, 1, 0.5 }) }; v1 = new Vector(new double[] { 0, 0, -1 }); v2 = new Vector(new double[] { 0, -1, 0 }); Vector v3 = new Vector(new double[] { -1, 0, 0 }); Vector v4 = new Vector(new double[] { -1, -1, -1 }); expect = new Hyperplane[] { new Hyperplane(points[3], v1), new Hyperplane(points[3], v2), new Hyperplane(points[3], v3), new Hyperplane(points[3], v4) }; yield return(new object[] { points, expect }); points = new PlanePoint[] { new PlanePoint(new double[] { 1, 1, 1 }), new PlanePoint(new double[] { 1, 5, 1 }), new PlanePoint(new double[] { 5, 1, 1 }), new PlanePoint(new double[] { 5, 5, 1 }), new PlanePoint(new double[] { 1, 1, 5 }), new PlanePoint(new double[] { 1, 5, 5 }), new PlanePoint(new double[] { 5, 1, 5 }), new PlanePoint(new double[] { 5, 5, 5 }), }; v1 = new Vector(new double[] { 0, 0, -1 }); v2 = new Vector(new double[] { 0, -1, 0 }); v3 = new Vector(new double[] { -1, 0, 0 }); v4 = new Vector(new double[] { -1, -1, -1 }); expect = new Hyperplane[] { new Hyperplane(points[0], v1), new Hyperplane(points[0], v2), new Hyperplane(points[0], v3), new Hyperplane(points[0], v4) }; yield return(new object[] { points, expect }); // points = new PlanePoint[] { // new PlanePoint(new double[]{4, 0, 0, 0}), // new PlanePoint(new double[]{0, 4, 0, 0}), // new PlanePoint(new double[]{0, 0, 4, 0}), // new PlanePoint(new double[]{0, 0, 0, 4}), // new PlanePoint(new double[]{0, 0, 0, 0}), // new PlanePoint(new double[]{0.5, 0.5, 0.5, 0.5}), // new PlanePoint(new double[]{1, 1, 1, 0.5}), // new PlanePoint(new double[]{3, 1, 1, 1}), // new PlanePoint(new double[]{1, 3, 1, 1}), // new PlanePoint(new double[]{1, 1, 3, 1}), // new PlanePoint(new double[]{1, 1, 1, 3}), // new PlanePoint(new double[]{1, 1, 1, 1}) // }; points = new PlanePoint[] { new PlanePoint(new double[] { 1, 1, 1, 1 }), new PlanePoint(new double[] { 5, 1, 1, 1 }), new PlanePoint(new double[] { 1, 5, 1, 1 }), new PlanePoint(new double[] { 5, 5, 1, 1 }), new PlanePoint(new double[] { 1, 1, 5, 1 }), new PlanePoint(new double[] { 5, 1, 5, 1 }), new PlanePoint(new double[] { 1, 5, 5, 1 }), new PlanePoint(new double[] { 5, 5, 5, 1 }), new PlanePoint(new double[] { 1, 1, 1, 5 }), new PlanePoint(new double[] { 5, 1, 1, 5 }), new PlanePoint(new double[] { 1, 5, 1, 5 }), new PlanePoint(new double[] { 5, 5, 1, 5 }), new PlanePoint(new double[] { 1, 1, 5, 5 }), new PlanePoint(new double[] { 5, 1, 5, 5 }), new PlanePoint(new double[] { 1, 5, 5, 5 }), new PlanePoint(new double[] { 5, 5, 5, 5 }), }; v1 = new Vector(new double[] { 0, 0, 0, -1 }); v2 = new Vector(new double[] { 0, 0, -1, 0 }); v3 = new Vector(new double[] { 0, -1, 0, 0 }); v4 = new Vector(new double[] { -1, 0, 0, 0 }); Vector v5 = new Vector(new double[] { -1, -1, -1, -1 }); expect = new Hyperplane[] { new Hyperplane(points[4], v1), new Hyperplane(points[4], v2), new Hyperplane(points[4], v3), new Hyperplane(points[4], v4), new Hyperplane(points[4], v5) }; yield return(new object[] { points, expect }); points = new PlanePoint[] { new PlanePoint(new double[] { 4, 0, 0, 0, 0 }), new PlanePoint(new double[] { 0, 4, 0, 0, 0 }), new PlanePoint(new double[] { 0, 0, 4, 0, 0 }), new PlanePoint(new double[] { 0, 0, 0, 4, 0 }), new PlanePoint(new double[] { 0, 0, 0, 0, 4 }), new PlanePoint(new double[] { 0, 0, 0, 0, 0 }), new PlanePoint(new double[] { 0.5, 0.5, 0.5, 0.5, 0 }), new PlanePoint(new double[] { 1, 1, 1, 0.5, 0.5 }), new PlanePoint(new double[] { 3, 1, 1, 1, 1 }), new PlanePoint(new double[] { 1, 3, 1, 1, 1 }), new PlanePoint(new double[] { 1, 1, 3, 1, 1 }), new PlanePoint(new double[] { 1, 1, 1, 3, 1 }), new PlanePoint(new double[] { 1, 1, 1, 1, 3 }), new PlanePoint(new double[] { 1, 1, 1, 1, 1 }) }; v1 = new Vector(new double[] { 0, 0, 0, 0, -1 }); v2 = new Vector(new double[] { 0, 0, 0, -1, 0 }); v3 = new Vector(new double[] { 0, 0, -1, 0, 0 }); v4 = new Vector(new double[] { 0, -1, 0, 0, 0 }); v5 = new Vector(new double[] { -1, 0, 0, 0, 0 }); Vector v6 = new Vector(new double[] { -1, -1, -1, -1 }); expect = new Hyperplane[] { new Hyperplane(points[5], v1), new Hyperplane(points[5], v2), new Hyperplane(points[5], v3), new Hyperplane(points[5], v4), new Hyperplane(points[5], v5) }; yield return(new object[] { points, expect }); }
public PlanePoint ConvertPoint_ReturnPlanePoint(Hyperplane h, Point p) { PlanePoint planePoint = h.ConvertPoint(p.ToPlanePoint()); return(planePoint); }