From 90c4a3300e9b49dcf09490681439949ac8919b71 Mon Sep 17 00:00:00 2001 From: alexej-jordan <58329349+alexej-jordan@users.noreply.github.com> Date: Thu, 24 Oct 2024 10:16:23 +0200 Subject: [PATCH] Improve stability of tests in PolyhedralGeometry (#4197) * introduced helper functions for stable tests in polyhedral geometry, applied to test/polyhedron.jl * increased stability for cone tests * increased stability for extended tests * increased stability for polyhedral_fan tests * increased stability for scalar_types tests * increased stability for polyhedral_complex tests * increased stability for subdivision_of_points tests * improved == for RayVector; forced RayVector != PointVector * fixed comparison between RayVectors; comparison between PointVector and RayVector now throws an error * fixed formatting for iterators.jl * added and adjusted commented test in cone.jl * increased code coverage for changes in iterators.jl * improved comparison between RayVectors * re-added test for matrix(ZZ, rays(Cone6)) * adjusted test for weights in subdivision_of_points.jl * improved comparison between RayVectors and added additional tests --- src/PolyhedralGeometry/iterators.jl | 21 +++++ test/PolyhedralGeometry/cone.jl | 82 ++++++++----------- test/PolyhedralGeometry/extended.jl | 14 ++-- test/PolyhedralGeometry/polyhedral_complex.jl | 30 +++---- test/PolyhedralGeometry/polyhedral_fan.jl | 30 ++++--- test/PolyhedralGeometry/polyhedron.jl | 24 ++---- test/PolyhedralGeometry/scalar_types.jl | 2 +- test/PolyhedralGeometry/setup_tests.jl | 24 ++++++ .../subdivision_of_points.jl | 10 +-- test/PolyhedralGeometry/types.jl | 19 ++++- 10 files changed, 139 insertions(+), 117 deletions(-) diff --git a/src/PolyhedralGeometry/iterators.jl b/src/PolyhedralGeometry/iterators.jl index 93f972e27575..f87b07a8d9d6 100644 --- a/src/PolyhedralGeometry/iterators.jl +++ b/src/PolyhedralGeometry/iterators.jl @@ -85,6 +85,27 @@ Return a `RayVector` resembling a ray from the origin through the point whose co """ ray_vector +function Base.:(==)(x::RayVector, y::RayVector) + ix = findfirst(!is_zero, x) + iy = findfirst(!is_zero, y) + ix == iy || return false + isnothing(ix) && return true + sign(x[ix]) == sign(y[iy]) || return false + return y[iy] * x.p == x[ix] * y.p +end + +function Base.:(==)(x::RayVector, y::AbstractVector) + ry = ray_vector(coefficient_field(x), y) + return x == ry +end + +Base.:(==)(x::AbstractVector, y::RayVector) = y == x + +Base.:(==)(::PointVector, ::RayVector) = + throw(ArgumentError("Cannot compare PointVector to RayVector")) +Base.:(==)(::RayVector, ::PointVector) = + throw(ArgumentError("Cannot compare PointVector to RayVector")) + ################################################################################ ######## Halfspaces and Hyperplanes ################################################################################ diff --git a/test/PolyhedralGeometry/cone.jl b/test/PolyhedralGeometry/cone.jl index 780870c10d2a..ba97410c6449 100644 --- a/test/PolyhedralGeometry/cone.jl +++ b/test/PolyhedralGeometry/cone.jl @@ -28,43 +28,38 @@ if T == QQFieldElem @test hilbert_basis(Cone1) isa SubObjectIterator{PointVector{ZZRingElem}} @test length(hilbert_basis(Cone1)) == 2 - @test hilbert_basis(Cone1) == [[1, 0], [0, 1]] - @test generator_matrix(hilbert_basis(Cone1)) == matrix(QQ, [1 0; 0 1]) + @test issetequal(hilbert_basis(Cone1), ray_vector.(Ref(ZZ), [[1, 0], [0, 1]])) + @test generator_matrix(hilbert_basis(Cone1)) == _oscar_matrix_from_property(ZZ, hilbert_basis(Cone1)) end @test n_rays(Cone1) == 2 @test rays(RayVector{T}, Cone1) isa SubObjectIterator{RayVector{T}} @test rays(Cone1) isa SubObjectIterator{RayVector{T}} @test rays(RayVector, Cone1) isa SubObjectIterator{RayVector{T}} - @test vector_matrix(rays(Cone1)) == matrix(f, [1 0; 0 1]) + @test issetequal(rays(Cone1), ray_vector.(Ref(f), [[1, 0], [0, 1]])) + @test vector_matrix(rays(Cone1)) == _oscar_matrix_from_property(f, rays(Cone1)) if T == QQFieldElem - @test matrix(QQ, rays(Cone1)) == matrix(QQ, [1 0; 0 1]) - @test matrix(ZZ, rays(Cone6)) == matrix(ZZ, [2 3; 2 5]) + @test matrix(QQ, rays(Cone1)) == _oscar_matrix_from_property(f, rays(Cone1)) + let r = rays(Cone6) + m = matrix(ZZ, r[1] == [1//3, 1//2] ? [2 3; 2 5] : [2 5; 2 3]) + @test matrix(ZZ, rays(Cone6)) == m + end end @test length(rays(Cone1)) == 2 - @test rays(Cone1) == [[1, 0], [0, 1]] - for S in [LinearHalfspace{T}, Cone{T}] + for S in [LinearHalfspace{T}, + Cone{T}] @test facets(S, Cone1) isa SubObjectIterator{S} @test length(facets(S, Cone1)) == 2 - if T == QQFieldElem - @test linear_inequality_matrix(facets(S, Cone1)) == matrix(QQ, [-1 0; 0 -1]) - @test Oscar.linear_matrix_for_polymake(facets(S, Cone1)) == [-1 0; 0 -1] - @test ray_indices(facets(S, Cone1)) == IncidenceMatrix([[2], [1]]) - @test IncidenceMatrix(facets(S, Cone1)) == IncidenceMatrix([[2], [1]]) - if S == LinearHalfspace{T} - @test facets(S, Cone1) == linear_halfspace.([f], [[-1, 0], [0, -1]]) - end + if S == LinearHalfspace{T} + @test issetequal(facets(S, Cone1), linear_halfspace.(Ref(f), [[-1, 0], [0, -1]])) else - @test linear_inequality_matrix(facets(S, Cone1)) == matrix(f, [0 -1; -1 0]) - @test Oscar.linear_matrix_for_polymake(facets(S, Cone1)) == [0 -1; -1 0] - @test ray_indices(facets(S, Cone1)) == IncidenceMatrix([[1], [2]]) - @test IncidenceMatrix(facets(S, Cone1)) == IncidenceMatrix([[1], [2]]) - if S == LinearHalfspace{T} - @test facets(S, Cone1) == linear_halfspace.([f], [[0, -1], [-1, 0]]) - end + @test issetequal(facets(S, Cone1), positive_hull.(Ref(f), [[1 0], [0 1]])) end + @test linear_inequality_matrix(facets(S, Cone1)) == _oscar_matrix_from_property(f, facets(S, Cone1)) + @test Oscar.linear_matrix_for_polymake(facets(S, Cone1)) == _polymake_matrix_from_property(facets(S, Cone1)) + @test _check_im_perm_rows(ray_indices(facets(S, Cone1)), [[1], [2]]) + @test _check_im_perm_rows(IncidenceMatrix(facets(S, Cone1)), [[1], [2]]) end - @test facets(IncidenceMatrix, Cone1) == - IncidenceMatrix(T == QQFieldElem ? [[2], [1]] : [[1], [2]]) + @test _check_im_perm_rows(facets(IncidenceMatrix, Cone1), [[1], [2]]) @test facets(Halfspace, Cone1) isa SubObjectIterator{LinearHalfspace{T}} @test facets(Cone1) isa SubObjectIterator{LinearHalfspace{T}} @test linear_span(Cone4) isa SubObjectIterator{LinearHyperplane{T}} @@ -92,43 +87,32 @@ end @test length(lineality_space(Cone2)) == 1 @test lineality_space(Cone2) == [L[1, :]] - @test vector_matrix(rays(Cone4)) == matrix(f, R) + @test vector_matrix(rays(Cone4)) == _oscar_matrix_from_property(f, rays(Cone4)) @test codim(Cone4) == 1 @test codim(Cone3) == 0 @test faces(Cone2, 2) isa SubObjectIterator{Cone{T}} @test length(faces(Cone2, 2)) == 2 @test faces(Cone4, 1) isa SubObjectIterator{Cone{T}} @test length(faces(Cone4, 1)) == 2 - if T == QQFieldElem - @test faces(Cone2, 2) == positive_hull.(T, [[0 0 1], [1 0 0]], [[0 1 0]]) - @test ray_indices(faces(Cone2, 2)) == IncidenceMatrix([[2], [1]]) - @test IncidenceMatrix(faces(Cone2, 2)) == IncidenceMatrix([[2], [1]]) - @test faces(IncidenceMatrix, Cone2, 2) == IncidenceMatrix([[2], [1]]) - @test faces(Cone4, 1) == positive_hull.(T, [[0 0 1], [1 0 0]]) - @test ray_indices(faces(Cone4, 1)) == IncidenceMatrix([[2], [1]]) - @test IncidenceMatrix(faces(Cone4, 1)) == IncidenceMatrix([[2], [1]]) - @test faces(IncidenceMatrix, Cone4, 1) == IncidenceMatrix([[2], [1]]) - else - @test faces(Cone2, 2) == positive_hull.([f], [[1 0 0], [0 0 1]], [[0 1 0]]) - @test ray_indices(faces(Cone2, 2)) == IncidenceMatrix([[1], [2]]) - @test IncidenceMatrix(faces(Cone2, 2)) == IncidenceMatrix([[1], [2]]) - @test faces(IncidenceMatrix, Cone2, 2) == IncidenceMatrix([[1], [2]]) - @test faces(Cone4, 1) == positive_hull.([f], [[1 0 0], [0 0 1]]) - @test ray_indices(faces(Cone4, 1)) == IncidenceMatrix([[1], [2]]) - @test IncidenceMatrix(faces(Cone4, 1)) == IncidenceMatrix([[1], [2]]) - @test faces(IncidenceMatrix, Cone4, 1) == IncidenceMatrix([[1], [2]]) - end - @test IncidenceMatrix(faces(Cone5, 1)) == IncidenceMatrix([[1], [2], [3], [4]]) + @test issetequal(faces(Cone2, 2), positive_hull.(Ref(f), [[1 0 0], [0 0 1]], [[0 1 0]])) + @test _check_im_perm_rows(ray_indices(faces(Cone2, 2)), [[1], [2]]) + @test _check_im_perm_rows(IncidenceMatrix(faces(Cone2, 2)), [[1], [2]]) + @test _check_im_perm_rows(faces(IncidenceMatrix, Cone2, 2), [[1], [2]]) + @test issetequal(faces(Cone4, 1), positive_hull.(Ref(f), [[0 0 1], [1 0 0]])) + @test _check_im_perm_rows(ray_indices(faces(Cone4, 1)), [[1], [2]]) + @test _check_im_perm_rows(IncidenceMatrix(faces(Cone4, 1)), [[1], [2]]) + @test _check_im_perm_rows(faces(IncidenceMatrix, Cone4, 1), [[1], [2]]) + @test _check_im_perm_rows(IncidenceMatrix(faces(Cone5, 1)), [[1], [2], [3], [4]]) @test isnothing(faces(Cone2, 1)) @test f_vector(Cone5) == [4, 4] @test f_vector(Cone2) == [0, 2] @test lineality_dim(Cone5) == 0 @test lineality_dim(Cone2) == 1 - @test facet_degrees(Cone5)[1] == 2 - @test facet_degrees(Cone6)[1] == 1 - @test ray_degrees(Cone5)[1] == 2 - @test ray_degrees(Cone6)[1] == 1 + @test facet_degrees(Cone5) == fill(2, 4) + @test facet_degrees(Cone6) == fill(1, 2) + @test ray_degrees(Cone5) == fill(2, 4) + @test ray_degrees(Cone6) == fill(1, 2) @test n_facets(Cone5) == 4 @test relative_interior_point(Cone1) == f.([1//2, 1//2]) diff --git a/test/PolyhedralGeometry/extended.jl b/test/PolyhedralGeometry/extended.jl index 2fcea73e3aca..10de0db2606e 100644 --- a/test/PolyhedralGeometry/extended.jl +++ b/test/PolyhedralGeometry/extended.jl @@ -83,29 +83,25 @@ f = sum([x; 1])^2 + x[1]^4 * x[2] * 3 newt = newton_polytope(f) @test dim(newt) == 2 - @test point_matrix(vertices(newt)) == matrix(QQ, [4 1; 2 0; 0 2; 0 0]) + @test issetequal(vertices(newt), point_vector.(Ref(QQ), [[4, 1], [2, 0], [0, 2], [0, 0]])) end @testset "Construct from QQFieldElem" begin A = zeros(Oscar.QQ, 3, 2) A[1, 1] = 1 A[3, 2] = 4 - @test point_matrix(vertices(convex_hull(A))) == matrix(QQ, [1 0; 0 0; 0 4]) + @test issetequal(vertices(convex_hull(A)), point_vector.(Ref(QQ), [[1, 0], [0, 0], [0, 4]])) - lhs, rhs = halfspace_matrix_pair(facets(polyhedron(A, [1, 2, -3]))) - @test lhs == matrix(QQ, [1 0; 0 4]) - @test rhs == [1, -3] + @test issetequal(facets(polyhedron(A, [1, 2, -3])), [affine_halfspace(QQ, [1, 0], 1), affine_halfspace(QQ, [0, 4], -3)]) end @testset "Construct from ZZRingElem" begin A = zeros(Oscar.ZZ, 3, 2) A[1, 1] = 1 A[3, 2] = 4 - @test point_matrix(vertices(convex_hull(A))) == matrix(QQ, [1 0; 0 0; 0 4]) + @test issetequal(vertices(convex_hull(A)), point_vector.(Ref(QQ), [[1, 0], [0, 0], [0, 4]])) - lhs, rhs = halfspace_matrix_pair(facets(polyhedron(A, [1, 2, -3]))) - @test lhs == matrix(QQ, [1 0; 0 4]) - @test rhs == [1, -3] + @test issetequal(facets(polyhedron(A, [1, 2, -3])), [affine_halfspace(QQ, [1, 0], 1), affine_halfspace(QQ, [0, 4], -3)]) end @testset "SubObjectIterator/Matrix compatibility" begin diff --git a/test/PolyhedralGeometry/polyhedral_complex.jl b/test/PolyhedralGeometry/polyhedral_complex.jl index 821eb959d87c..45aaa618e7ad 100644 --- a/test/PolyhedralGeometry/polyhedral_complex.jl +++ b/test/PolyhedralGeometry/polyhedral_complex.jl @@ -34,44 +34,36 @@ # test constructor with re-arranged arguments let PCF2 = polyhedral_complex(f, -P[1:3, :], I[:, 1:3], -P[4:4, :], I[:, 4:4]) - @test vertices(PCF) == vertices(PCF2) - @test rays(PCF) == rays(PCF2) - @test IncidenceMatrix(maximal_polyhedra(PCF)) == - IncidenceMatrix(maximal_polyhedra(PCF2)) + @test issetequal(vertices(PCF), vertices(PCF2)) + @test issetequal(rays(PCF), rays(PCF2)) + @test issetequal(maximal_polyhedra(PCF), maximal_polyhedra(PCF2)) end @testset "core functionality" begin @test ambient_dim(PC) == 2 @test vertices(PC) isa SubObjectIterator{PointVector{T}} @test length(vertices(PC)) == 4 - @test point_matrix(vertices(PC)) == matrix(f, P) - @test vertices(PC) == [[0, 0], [1, 0], [0, 1], [1, 1]] + @test issetequal(vertices(PC), point_vector.(Ref(f), [[0, 0], [1, 0], [0, 1], [1, 1]])) + @test point_matrix(vertices(PC)) == _oscar_matrix_from_property(f, vertices(PC)) @test rays(PCF) isa SubObjectIterator{RayVector{T}} @test length(rays(PCF)) == 1 @test rays(PCF) == [[-1, -1]] @test vector_matrix(rays(PCF)) == matrix(f, [-1 -1]) @test vertices_and_rays(PCFL) isa SubObjectIterator{Union{RayVector{T},PointVector{T}}} @test length(vertices_and_rays(PCFL)) == 4 - @test vertices_and_rays(PCFL) == [[0, 0, 0], [1, 0, 0], [0, 1, 0], [1, 1, 0]] - @test typeof.(vertices_and_rays(PCFL)) == - [PointVector{T}, PointVector{T}, PointVector{T}, RayVector{T}] - @test vector_matrix(vertices_and_rays(PCFL)) == matrix(f, P2) + @test issetequal(vertices_and_rays(PCFL), [point_vector(f, [0, 0, 0]), point_vector(f, [1, 0, 0]), point_vector(f, [0, 1, 0]), ray_vector(f, [1, 1, 0])]) + @test vector_matrix(vertices_and_rays(PCFL)) == _oscar_matrix_from_property(f, vertices_and_rays(PCFL)) @test maximal_polyhedra(PC) isa SubObjectIterator{Polyhedron{T}} @test length(maximal_polyhedra(PC)) == 2 - @test maximal_polyhedra(PC) == convex_hull.([f], [P[1:3, :], P[[2, 4], :]]) + @test issetequal(maximal_polyhedra(PC), convex_hull.([f], [P[1:3, :], P[[2, 4], :]])) @test number_of_maximal_polyhedra(PC) == 2 @test is_simplicial(PC) @test !is_pure(PCL) @test dim(PCL) == 3 @test polyhedra_of_dim(PC, 1) isa SubObjectIterator{Polyhedron{T}} @test length(polyhedra_of_dim(PC, 1)) == 4 - if T == QQFieldElem - @test polyhedra_of_dim(PC, 1) == - convex_hull.(T, [P[[2, 4], :], P[[1, 3], :], P[[1, 2], :], P[[2, 3], :]]) - else - @test polyhedra_of_dim(PC, 1) == - convex_hull.([f], [P[[2, 4], :], P[[1, 3], :], P[[2, 3], :], P[[1, 2], :]]) - end + @test issetequal(polyhedra_of_dim(PC, 1), + convex_hull.(Ref(f), [P[[2, 4], :], P[[1, 3], :], P[[2, 3], :], P[[1, 2], :]])) @test lineality_space(PCL) isa SubObjectIterator{RayVector{T}} @test length(lineality_space(PCL)) == 1 @test lineality_space(PCL) == [L[:]] @@ -125,7 +117,7 @@ @test dim(F) == dim(PC) @test ambient_dim(F) == ambient_dim(PC) @test lineality_dim(F) == lineality_dim(PC) - @test matrix(f, rays(F)) == matrix(f, rays(PC)) + @test issetequal(rays(F), rays(PC)) @test n_maximal_cones(F) == n_maximal_polyhedra(PC) vrep = PolyhedralComplex{T}( Polymake.fan.PolyhedralComplex(; diff --git a/test/PolyhedralGeometry/polyhedral_fan.jl b/test/PolyhedralGeometry/polyhedral_fan.jl index 8e1c02e3f081..e012d5615d7b 100644 --- a/test/PolyhedralGeometry/polyhedral_fan.jl +++ b/test/PolyhedralGeometry/polyhedral_fan.jl @@ -28,10 +28,10 @@ if T == QQFieldElem @test is_smooth(NFsquare) end - @test vector_matrix(rays(NFsquare)) == matrix(f, [1 0; -1 0; 0 1; 0 -1]) @test rays(NFsquare) isa SubObjectIterator{RayVector{T}} @test length(rays(NFsquare)) == 4 - @test rays(NFsquare) == [[1, 0], [-1, 0], [0, 1], [0, -1]] + @test issetequal(rays(NFsquare), ray_vector.(Ref(f), [[1, 0], [-1, 0], [0, 1], [0, -1]])) + @test vector_matrix(rays(NFsquare)) == _oscar_matrix_from_property(f, rays(NFsquare)) @test is_regular(NFsquare) @test is_complete(NFsquare) @test !is_complete(F0) @@ -45,25 +45,23 @@ @test length(RMLF2[:rays_modulo_lineality]) == 2 @test maximal_cones(F1) isa SubObjectIterator{Cone{T}} @test dim.(maximal_cones(F1)) == [2, 2] - @test ray_indices(maximal_cones(F1)) == incidence1 - @test IncidenceMatrix(maximal_cones(F1)) == incidence1 - @test maximal_cones(IncidenceMatrix, F1) == incidence1 + @test _check_im_perm_rows(ray_indices(maximal_cones(F1)), incidence1) + @test _check_im_perm_rows(IncidenceMatrix(maximal_cones(F1)), incidence1) + @test _check_im_perm_rows(maximal_cones(IncidenceMatrix, F1), incidence1) @test number_of_maximal_cones(F1) == 2 @test lineality_space(F2) isa SubObjectIterator{RayVector{T}} - @test generator_matrix(lineality_space(F2)) == matrix(f, L) - if T == QQFieldElem - @test matrix(QQ, lineality_space(F2)) == matrix(QQ, L) - end @test length(lineality_space(F2)) == 1 @test lineality_space(F2) == [L[:]] + @test generator_matrix(lineality_space(F2)) == matrix(f, L) + @test matrix(f, lineality_space(F2)) == matrix(f, L) @test cones(F2, 2) isa SubObjectIterator{Cone{T}} @test size(cones(F2, 2)) == (2,) @test lineality_space(cones(F2, 2)[1]) == [[0, 1, 0]] @test rays.(cones(F2, 2)) == [[], []] @test isnothing(cones(F2, 1)) - @test ray_indices(cones(F1, 2)) == incidence1 - @test IncidenceMatrix(cones(F1, 2)) == incidence1 - @test cones(IncidenceMatrix, F1, 2) == incidence1 + @test _check_im_perm_rows(ray_indices(cones(F1, 2)), incidence1) + @test _check_im_perm_rows(IncidenceMatrix(cones(F1, 2)), incidence1) + @test _check_im_perm_rows(cones(IncidenceMatrix, F1, 2), incidence1) II = ray_indices(maximal_cones(NFsquare)) NF0 = polyhedral_fan(II, rays(NFsquare)) @@ -75,16 +73,16 @@ end @test f_vector(NFsquare) == [4, 4] @test rays(F1NR) == collect(eachrow(I3)) - @test ray_indices(maximal_cones(F1NR)) == incidence1 - @test IncidenceMatrix(maximal_cones(F1NR)) == incidence1 + @test _check_im_perm_rows(ray_indices(maximal_cones(F1NR)), incidence1) + @test _check_im_perm_rows(IncidenceMatrix(maximal_cones(F1NR)), incidence1) @test n_rays(F2NR) == 0 @test lineality_dim(F2NR) == 1 RMLF2NR = rays_modulo_lineality(F2NR) @test length(RMLF2NR[:rays_modulo_lineality]) == 2 @test RMLF2NR[:rays_modulo_lineality] == collect(eachrow(R)) @test lineality_space(F2NR) == collect(eachrow(L)) - @test ray_indices(maximal_cones(F2NR)) == incidence2 - @test IncidenceMatrix(maximal_cones(F2NR)) == incidence2 + @test _check_im_perm_rows(ray_indices(maximal_cones(F2NR)), incidence2) + @test _check_im_perm_rows(IncidenceMatrix(maximal_cones(F2NR)), incidence2) C = positive_hull(f, identity_matrix(ZZ, 0)) pf = polyhedral_fan(C) diff --git a/test/PolyhedralGeometry/polyhedron.jl b/test/PolyhedralGeometry/polyhedron.jl index 1445276d7405..405e7a31cbfb 100644 --- a/test/PolyhedralGeometry/polyhedron.jl +++ b/test/PolyhedralGeometry/polyhedron.jl @@ -37,14 +37,6 @@ @test nrows(Oscar.pm_object(pf3).INEQUALITIES) == 4 @test n_vertices(pf3) == 1 - function _check_im_perm_rows(inc::IncidenceMatrix, o) - oinc = IncidenceMatrix(o) - nr = nrows(inc) - nr == nrows(oinc) && - issetequal(Polymake.row.(Ref(inc), 1:nr), - Polymake.row.(Ref(oinc), 1:nr)) - end - @testset "core functionality" begin @test matrix(f, rays(Q1)) * v == T[f(2)] @test issetequal(matrix(f, vertices(Q1)) * v, T[f(1), f(0), f(1)]) @@ -55,20 +47,20 @@ @test n_vertices(Q0) == 3 @test n_vertices.(faces(Q0, 1)) == [2, 2, 2] @test lattice_points(Q0) isa SubObjectIterator{PointVector{ZZRingElem}} - @test point_matrix(lattice_points(Q0)) isa MatElem{ZZRingElem} - @test matrix(ZZ, lattice_points(Q0)) isa MatElem{ZZRingElem} @test length(lattice_points(Q0)) == 3 @test issetequal(lattice_points(Q0), point_vector.(Ref(ZZ), [[0, 0], [0, 1], [1, 0]])) + @test point_matrix(lattice_points(Q0)) == _oscar_matrix_from_property(ZZ, lattice_points(Q0)) + @test matrix(ZZ, lattice_points(Q0)) == _oscar_matrix_from_property(ZZ, lattice_points(Q0)) @test interior_lattice_points(square) isa SubObjectIterator{PointVector{ZZRingElem}} @test point_matrix(interior_lattice_points(square)) == matrix(ZZ, [0 0]) @test matrix(ZZ, interior_lattice_points(square)) == matrix(ZZ, [0 0]) @test length(interior_lattice_points(square)) == 1 @test interior_lattice_points(square) == [[0, 0]] @test boundary_lattice_points(square) isa SubObjectIterator{PointVector{ZZRingElem}} - @test point_matrix(boundary_lattice_points(square)) isa MatElem{ZZRingElem} @test length(boundary_lattice_points(square)) == 8 @test issetequal(boundary_lattice_points(square), point_vector.(Ref(ZZ), [[-1, -1], [-1, 0], [-1, 1], [0, -1], [0, 1], [1, -1], [1, 0], [1, 1]])) + @test point_matrix(boundary_lattice_points(square)) == _oscar_matrix_from_property(ZZ, boundary_lattice_points(square)) if T == QQFieldElem @test is_smooth(Q0) @test is_normal(Q0) @@ -111,8 +103,8 @@ @test rays(RayVector, Pos) isa SubObjectIterator{RayVector{T}} @test rays(Pos) isa SubObjectIterator{RayVector{T}} @test length(rays(Pos)) == 3 - @test vector_matrix(rays(Pos)) isa MatElem{T} @test issetequal(rays(Pos), ray_vector.(Ref(f), [[1, 0, 0], [0, 1, 0], [0, 0, 1]])) + @test vector_matrix(rays(Pos)) == _oscar_matrix_from_property(f, rays(Pos)) @test lineality_space(L) isa SubObjectIterator{RayVector{T}} @test generator_matrix(lineality_space(L)) == matrix(f, [0 0 1]) if T == QQFieldElem @@ -151,7 +143,7 @@ v = vertices(minkowski_sum(Q0, square)) @test length(v) == 5 @test issetequal(v, point_vector.(Ref(f), [[2, -1], [2, 1], [-1, -1], [-1, 2], [1, 2]])) - @test point_matrix(v) isa MatElem{T} + @test point_matrix(v) == _oscar_matrix_from_property(f, v) let S = Pair{Matrix{T},T} @test issetequal(facets(S, Pos), S.([f.([-1 0 0]), f.([0 -1 0]), f.([0 0 -1])], [f(0)])) end @@ -190,13 +182,11 @@ @test facets(Pos) isa SubObjectIterator{AffineHalfspace{T}} @test facets(Halfspace, Pos) isa SubObjectIterator{AffineHalfspace{T}} @test affine_hull(point) isa SubObjectIterator{AffineHyperplane{T}} - @test affine_equation_matrix(affine_hull(point)) isa MatElem{T} - @test size(affine_equation_matrix(affine_hull(point))) == (3, 4) - @test Oscar.affine_matrix_for_polymake(affine_hull(point)) isa Polymake.Matrix{Oscar._scalar_type_to_polymake(T)} - @test size(Oscar.affine_matrix_for_polymake(affine_hull(point))) == (3, 4) @test length(affine_hull(point)) == 3 @test issetequal(affine_hull(point), [hyperplane(f, [1 0 0], 0), hyperplane(f, [0 1 0], 1), hyperplane(f, [0 0 1], 0)]) + @test affine_equation_matrix(affine_hull(point)) == _oscar_matrix_from_property(f, affine_hull(point)) + @test Oscar.affine_matrix_for_polymake(affine_hull(point)) == _polymake_matrix_from_property(affine_hull(point)) @test n_facets(square) == 4 @test lineality_dim(Q0) == 0 @test n_rays(Q1) == 1 diff --git a/test/PolyhedralGeometry/scalar_types.jl b/test/PolyhedralGeometry/scalar_types.jl index 8e67d92d98e6..802b1794a306 100644 --- a/test/PolyhedralGeometry/scalar_types.jl +++ b/test/PolyhedralGeometry/scalar_types.jl @@ -49,7 +49,7 @@ let pc = polyhedral_complex( E, IncidenceMatrix(facets(sd)), vertices(sd); non_redundant=true ) - @test maximal_polyhedra(pc) == faces(sd, 2) + @test issetequal(maximal_polyhedra(pc), faces(sd, 2)) end let c = convex_hull(E, permutedims([0]), permutedims([r])) ms = product(sd, c) diff --git a/test/PolyhedralGeometry/setup_tests.jl b/test/PolyhedralGeometry/setup_tests.jl index d7087e22adaa..6d2ba9757c99 100644 --- a/test/PolyhedralGeometry/setup_tests.jl +++ b/test/PolyhedralGeometry/setup_tests.jl @@ -7,3 +7,27 @@ if !isdefined(Main, :_prepare_scalar_types) return [(f, elem_type(f)) for f in (QQ, K, KK)] end end + +function _check_im_perm_rows(inc::IncidenceMatrix, o) + oinc = IncidenceMatrix(o) + nr, nc = size(inc) + (nr, nc) == size(oinc) && + issetequal(Polymake.row.(Ref(inc), 1:nr), + Polymake.row.(Ref(oinc), 1:nr)) +end + +_matrix_from_property(b::SubObjectIterator{<:Union{LinearHalfspace, LinearHyperplane}}) = permutedims(hcat([normal_vector(be) for be in b]...)) + +_matrix_from_property(b::SubObjectIterator{<:Union{AffineHalfspace, AffineHyperplane}}) = permutedims(hcat([vcat(-negbias(be), normal_vector(be)) for be in b]...)) + +# only used for cones that are linear halfspaces +_matrix_from_property(b::SubObjectIterator{Cone{T}}) where T = _matrix_from_property(SubObjectIterator{LinearHalfspace{T}}(b.Obj, b.Acc, b.n)) + +_matrix_from_property(b::SubObjectIterator) = permutedims(hcat(b...)) + +_oscar_matrix_from_property(a, b::SubObjectIterator) = matrix(a, _matrix_from_property(b)) + +function _polymake_matrix_from_property(b::SubObjectIterator) + m = _matrix_from_property(b) + return Polymake.Matrix{Oscar._scalar_type_to_polymake(eltype(m))}(m) +end diff --git a/test/PolyhedralGeometry/subdivision_of_points.jl b/test/PolyhedralGeometry/subdivision_of_points.jl index 6d4c241386ef..2608f0e46f6f 100644 --- a/test/PolyhedralGeometry/subdivision_of_points.jl +++ b/test/PolyhedralGeometry/subdivision_of_points.jl @@ -14,9 +14,9 @@ SubdivisionOfPoints @testset "alternative inputs" begin - @test issetequal(collect(maximal_cells(square_by_incidence)), - collect(maximal_cells(square_by_weights))) - @test min_weights(square_by_cells) == min_weights(square_by_weights) + @test issetequal(maximal_cells(square_by_incidence), + maximal_cells(square_by_weights)) + @test issetequal(square_max_cells, maximal_cells(subdivision_of_points(C,min_weights(square_by_cells)))) end moaepts = [4 0 0; 0 4 0; 0 0 4; 2 1 1; 1 2 1; 1 1 2] @@ -45,10 +45,10 @@ @test min_weights(SOP1) == [0, 0, 0, 1, 1, 1] @test dim(C1) == 6 @test dim(CMOAE) == 4 - @test moaeimnonreg0 == maximal_cells(IncidenceMatrix, MOAE) + @test _check_im_perm_rows(moaeimnonreg0, maximal_cells(IncidenceMatrix, MOAE)) @test number_of_points(MOAE) == 6 @test length(points(MOAE)) == 6 - @test collect(points(MOAE))[3] == [0, 0, 4] + @test [0, 0, 4] in points(MOAE) @test gkz_vector(fulldim_MOAE) == [9, 9, 9, 7, 7, 7] end end diff --git a/test/PolyhedralGeometry/types.jl b/test/PolyhedralGeometry/types.jl index af613877f754..f54e31a349b7 100644 --- a/test/PolyhedralGeometry/types.jl +++ b/test/PolyhedralGeometry/types.jl @@ -14,7 +14,7 @@ (ENF, _) = _prepare_scalar_types()[2] - @testset "$T" for (T, fun) in ((PointVector, point_vector), (RayVector, ray_vector)) + @testset "$T" for (T, fun, other) in ((PointVector, point_vector, ray_vector), (RayVector, ray_vector, point_vector)) @test fun(a) isa T{QQFieldElem} for f in (ZZ, QQ, ENF) @@ -57,6 +57,10 @@ @test *(g(3), A) isa T @test *(g(3), A) == 3 * a + + let Ao = other(g, a) + @test_throws ArgumentError A == Ao + end end for op in [+, -] @@ -69,6 +73,19 @@ @test 3 * A isa T{U} @test 3 * A == 3 * a + if T == RayVector + @test 5 * A == A + @test fun(f, 5 * a) == A + @test A == fun(f, 5 * a) + @test 5 * a == A + @test vcat(a, a) != A + @test -5 * A != A + @test fun(f, -5 * a) != A + @test A != fun(f, -5 * a) + @test A == 5 * a + @test A != vcat(a, a) + end + if f != ENF let h = Int Ah = h.(A)