mirror of
https://github.com/kalmarek/Groups.jl.git
synced 2024-12-03 17:56:28 +01:00
Merge branch 'enh/type_ovehaul'
This commit is contained in:
commit
342d842585
@ -9,13 +9,14 @@ export DirectProductGroup, DirectProductGroupElem
|
||||
###############################################################################
|
||||
|
||||
doc"""
|
||||
DirectProductGroup(factors::Vector{Group}) <: Group
|
||||
Implements direct product of groups as vector factors. The group operation is
|
||||
DirectProductGroup(G::Group, n::Int) <: Group
|
||||
Implements `n`-fold direct product of `G`. The group operation is
|
||||
`*` distributed component-wise, with component-wise identity as neutral element.
|
||||
"""
|
||||
|
||||
immutable DirectProductGroup{T<:Group} <: Group
|
||||
factors::Vector{T}
|
||||
group::T
|
||||
n::Int
|
||||
end
|
||||
|
||||
immutable DirectProductGroupElem{T<:GroupElem} <: GroupElem
|
||||
@ -28,11 +29,14 @@ end
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
elem_type{T<:Group}(G::DirectProductGroup{T}) = DirectProductGroupElem{elem_type(first(G.factors))}
|
||||
elem_type{T<:Group}(G::DirectProductGroup{T}) =
|
||||
DirectProductGroupElem{elem_type(G.group)}
|
||||
|
||||
parent_type(::Type{DirectProductGroupElem}) = DirectProductGroup
|
||||
parent_type{T<:GroupElem}(::Type{DirectProductGroupElem{T}}) =
|
||||
DirectProductGroup{parent_type(T)}
|
||||
|
||||
parent(g::DirectProductGroupElem) = DirectProductGroup([parent(h) for h in g.elts])
|
||||
parent(g::DirectProductGroupElem) =
|
||||
DirectProductGroup(parent(first(g.elts)), length(g.elts))
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
@ -44,8 +48,9 @@ Base.size(g::DirectProductGroupElem) = size(g.elts)
|
||||
Base.linearindexing(::Type{DirectProductGroupElem}) = Base.LinearFast()
|
||||
Base.getindex(g::DirectProductGroupElem, i::Int) = g.elts[i]
|
||||
function Base.setindex!{T<:GroupElem}(g::DirectProductGroupElem{T}, v::T, i::Int)
|
||||
p.part[i] = v
|
||||
return p
|
||||
parent(v) == parent(first(g.elts)) || throw("$g is not an element of $i-th factor of $(parent(G))")
|
||||
g.elts[i] = v
|
||||
return g
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
@ -54,9 +59,10 @@ end
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
DirectProductGroup{T<:Group}(G::T, H::T) = DirectProductGroup{T}([G, H])
|
||||
|
||||
×(G::Group, H::Group) = DirectProductGroup([G,H])
|
||||
function ×(G::Group, H::Group)
|
||||
G == H || throw("Direct products are defined only for the same groups")
|
||||
return DirectProductGroup(G,2)
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
@ -64,23 +70,25 @@ DirectProductGroup{T<:Group}(G::T, H::T) = DirectProductGroup{T}([G, H])
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
(G::DirectProductGroup)() = G([H() for H in G.factors])
|
||||
doc"""
|
||||
(G::DirectProductGroup)(a::Vector, check::Bool=true)
|
||||
> Constructs element of the $n$-fold direct product group `G` by coercing each
|
||||
> element of vector `a` to `G.group`. If `check` flag is set to `false` neither
|
||||
> check on the correctness nor coercion is performed.
|
||||
"""
|
||||
function (G::DirectProductGroup)(a::Vector, check::Bool=true)
|
||||
if check
|
||||
G.n == length(a) || throw("Can not coerce to DirectProductGroup: lengths differ")
|
||||
a = G.group.(a)
|
||||
end
|
||||
return DirectProductGroupElem(a)
|
||||
end
|
||||
|
||||
(G::DirectProductGroup)() = DirectProductGroupElem([G.group() for _ in 1:G.n])
|
||||
|
||||
(G::DirectProductGroup)(g::DirectProductGroupElem) = G(g.elts)
|
||||
|
||||
doc"""
|
||||
(G::DirectProductGroup)(a::Vector; checked=true)
|
||||
> Constructs element of the direct product group `G` by coercing each element
|
||||
> of vector `a` to the corresponding factor of `G`. If `checked` flag is set to
|
||||
> `false` no checks on the correctness are performed.
|
||||
|
||||
"""
|
||||
function (G::DirectProductGroup){T<:GroupElem}(a::Vector{T})
|
||||
length(a) == length(G.factors) || throw("Cannot coerce $a to $G: they have
|
||||
different number of factors")
|
||||
@assert elem_type(first(G.factors)) == T
|
||||
return DirectProductGroupElem(a)
|
||||
end
|
||||
(G::DirectProductGroup){T<:GroupElem, N}(a::Vararg{T, N}) = G([a...])
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
@ -94,20 +102,13 @@ function deepcopy_internal(g::DirectProductGroupElem, dict::ObjectIdDict)
|
||||
end
|
||||
|
||||
function hash(G::DirectProductGroup, h::UInt)
|
||||
return hash(G.factors, hash(DirectProductGroup,h))
|
||||
return hash(G.group, hash(G.n, hash(DirectProductGroup,h)))
|
||||
end
|
||||
|
||||
function hash(g::DirectProductGroupElem, h::UInt)
|
||||
return hash(g.elts, hash(parent(g), hash(DirectProductGroupElem, h)))
|
||||
end
|
||||
|
||||
doc"""
|
||||
eye(G::DirectProductGroup)
|
||||
> Return the identity element for the given direct product of groups.
|
||||
|
||||
"""
|
||||
eye(G::DirectProductGroup) = G()
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
# String I/O
|
||||
@ -115,12 +116,11 @@ eye(G::DirectProductGroup) = G()
|
||||
###############################################################################
|
||||
|
||||
function show(io::IO, G::DirectProductGroup)
|
||||
println(io, "Direct product of groups")
|
||||
join(io, G.factors, ", ", " and ")
|
||||
println(io, "$(G.n)-fold direct product of $(G.group)")
|
||||
end
|
||||
|
||||
function show(io::IO, g::DirectProductGroupElem)
|
||||
print(io, "("*join(g.elts,",")*")")
|
||||
print(io, "($(join(g.elts,",")))")
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
@ -129,65 +129,62 @@ end
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
doc"""
|
||||
==(g::DirectProductGroup, h::DirectProductGroup)
|
||||
> Checks if two direct product groups are the same.
|
||||
"""
|
||||
function (==)(G::DirectProductGroup, H::DirectProductGroup)
|
||||
G.factors == H.factors || return false
|
||||
G.group == H.group || return false
|
||||
G.n == G.n || return false
|
||||
return true
|
||||
end
|
||||
|
||||
doc"""
|
||||
==(g::DirectProductGroupElem, h::DirectProductGroupElem)
|
||||
> Return `true` if the given elements of direct products are equal, otherwise return `false`.
|
||||
|
||||
> Checks if two direct product group elements are the same.
|
||||
"""
|
||||
function (==)(g::DirectProductGroupElem, h::DirectProductGroupElem)
|
||||
parent(g) == parent(h) || return false
|
||||
g.elts == h.elts || return false
|
||||
return true
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
# Binary operators
|
||||
# Group operations
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
function direct_mult(g::DirectProductGroupElem, h::DirectProductGroupElem)
|
||||
G = parent(g)
|
||||
# G == parent(h) || throw("Can't multiply elements from different groups: $G, $parent(h)")
|
||||
if isa(first(G.factors), Ring)
|
||||
return G(.+(g.elts,h.elts))
|
||||
else
|
||||
return G(.*(g.elts,h.elts))
|
||||
end
|
||||
end
|
||||
|
||||
doc"""
|
||||
*(g::DirectProductGroupElem, h::DirectProductGroupElem)
|
||||
> Return the direct-product group operation of elements, i.e. component-wise
|
||||
> operation as defined by `operations` field of the parent object.
|
||||
|
||||
"""
|
||||
(*)(g::DirectProductGroupElem, h::DirectProductGroupElem) = direct_mult(g,h)
|
||||
# TODO: dirty hack around `+/*` operations
|
||||
function *{T<:GroupElem}(g::DirectProductGroupElem{T}, h::DirectProductGroupElem{T}, check::Bool=true)
|
||||
if check
|
||||
parent(g) == parent(h) || throw("Can not multiply elements of different groups!")
|
||||
end
|
||||
return DirectProductGroupElem([a*b for (a,b) in zip(g.elts,h.elts)])
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
# Inversion
|
||||
#
|
||||
###############################################################################
|
||||
function *{T<:RingElem}(g::DirectProductGroupElem{T}, h::DirectProductGroupElem{T}, check::Bool=true)
|
||||
if check
|
||||
parent(g) == parent(h) || throw("Can not multiply elements of different groups!")
|
||||
end
|
||||
return DirectProductGroupElem(g.elts + h.elts)
|
||||
end
|
||||
|
||||
doc"""
|
||||
inv(g::DirectProductGroupElem)
|
||||
> Return the inverse of the given element in the direct product group.
|
||||
|
||||
"""
|
||||
# TODO: dirty hack around `+` operation
|
||||
function inv(g::DirectProductGroupElem)
|
||||
G = parent(g)
|
||||
if isa(first(G.factors), Ring)
|
||||
return DirectProductGroupElem([-a for a in g.elts])
|
||||
else
|
||||
return DirectProductGroupElem([inv(a) for a in g.elts])
|
||||
end
|
||||
# TODO: dirty hack around `+/*` operation
|
||||
function inv{T<:GroupElem}(g::DirectProductGroupElem{T})
|
||||
return DirectProductGroupElem([inv(a) for a in g.elts])
|
||||
end
|
||||
|
||||
function inv{T<:RingElem}(g::DirectProductGroupElem{T})
|
||||
return DirectProductGroupElem(-g.elts)
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
@ -198,15 +195,15 @@ end
|
||||
|
||||
doc"""
|
||||
elements(G::DirectProductGroup)
|
||||
> Returns `Task` that produces all elements of group `G` (provided that factors
|
||||
> implement the elements function).
|
||||
|
||||
> Returns `generator` that produces all elements of group `G` (provided that
|
||||
> `G.group` implements the `elements` method).
|
||||
"""
|
||||
# TODO: can Base.product handle generators?
|
||||
# now it returns nothing's so we have to collect ellements...
|
||||
function elements(G::DirectProductGroup)
|
||||
cartesian_prod = Base.product([collect(elements(H)) for H in G.factors]...)
|
||||
return (G(collect(elt)) for elt in cartesian_prod)
|
||||
elts = collect(elements(G.group))
|
||||
cartesian_prod = Base.product([elts for _ in 1:G.n]...)
|
||||
return (DirectProductGroupElem([elt...]) for elt in cartesian_prod)
|
||||
end
|
||||
|
||||
doc"""
|
||||
@ -214,4 +211,4 @@ doc"""
|
||||
> Returns the order (number of elements) in the group.
|
||||
|
||||
"""
|
||||
order(G::DirectProductGroup) = prod([order(H) for H in G.factors])
|
||||
order(G::DirectProductGroup) = order(G.group)^G.n
|
||||
|
@ -7,35 +7,38 @@ export WreathProduct, WreathProductElem
|
||||
###############################################################################
|
||||
|
||||
doc"""
|
||||
WreathProduct <: Group
|
||||
> Implements Wreath product of a group N by permutation (sub)group P < Sₖ,
|
||||
WreathProduct{T<:Group} <: Group
|
||||
> Implements Wreath product of a group $N$ by permutation (sub)group $P < S_k$,
|
||||
> usually written as $N \wr P$.
|
||||
> The multiplication inside wreath product is defined as
|
||||
> (n, σ) * (m, τ) = (n*ψ(σ)(m), σ*τ),
|
||||
> where ψ:P → Aut(Nᵏ) is the permutation representation of Sₖ restricted to P.
|
||||
> $$(n, \sigma) * (m, \tau) = (n\psi(\sigma)(m), \sigma\tau),$$
|
||||
> where $\psi:P → Aut(N^k)$ is the permutation representation of $S_k$
|
||||
> restricted to $P$.
|
||||
|
||||
# Arguments:
|
||||
* `::Group` : the single factor of group N
|
||||
* `::PermutationGroup` : full PermutationGroup
|
||||
* `::Group` : the single factor of group $N$
|
||||
* `::PermGroup` : full `PermutationGroup`
|
||||
"""
|
||||
immutable WreathProduct{T<:Group} <: Group
|
||||
N::DirectProductGroup{T}
|
||||
P::PermGroup
|
||||
|
||||
type WreathProduct <: Group
|
||||
N::DirectProductGroup
|
||||
P::PermutationGroup
|
||||
|
||||
function WreathProduct(G::Group, P::PermutationGroup)
|
||||
N = DirectProductGroup(typeof(G)[G for _ in 1:P.n])
|
||||
function WreathProduct(G::Group, P::PermGroup)
|
||||
N = DirectProductGroup(G, P.n)
|
||||
return new(N, P)
|
||||
end
|
||||
end
|
||||
|
||||
type WreathProductElem <: GroupElem
|
||||
n::DirectProductGroupElem
|
||||
immutable WreathProductElem{T<:GroupElem} <: GroupElem
|
||||
n::DirectProductGroupElem{T}
|
||||
p::perm
|
||||
parent::WreathProduct
|
||||
# parent::WreathProduct
|
||||
|
||||
function WreathProductElem(n::DirectProductGroupElem, p::perm)
|
||||
length(n.elts) == parent(p).n
|
||||
function WreathProductElem(n::DirectProductGroupElem, p::perm,
|
||||
check::Bool=true)
|
||||
if check
|
||||
length(n.elts) == parent(p).n || throw("Can't form WreathProductElem: lengths differ")
|
||||
end
|
||||
return new(n, p)
|
||||
end
|
||||
end
|
||||
@ -46,11 +49,12 @@ end
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
elem_type(::WreathProduct) = WreathProductElem
|
||||
elem_type{T<:Group}(::WreathProduct{T}) = WreathProductElem{elem_type(T)}
|
||||
|
||||
parent_type(::WreathProductElem) = WreathProduct
|
||||
parent_type{T<:GroupElem}(::Type{WreathProductElem{T}}) =
|
||||
WreathProduct{parent_type(T)}
|
||||
|
||||
parent(g::WreathProductElem) = g.parent
|
||||
parent(g::WreathProductElem) = WreathProduct(parent(g.n[1]), parent(g.p))
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
@ -58,7 +62,10 @@ parent(g::WreathProductElem) = g.parent
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
# converts???
|
||||
WreathProduct{T<:Group}(G::T, P::PermGroup) = WreathProduct{T}(G, P)
|
||||
|
||||
WreathProductElem{T<:GroupElem}(n::DirectProductGroupElem{T},
|
||||
p::perm, check::Bool=true) = WreathProductElem{T}(n, p, check)
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
@ -67,39 +74,31 @@ parent(g::WreathProductElem) = g.parent
|
||||
###############################################################################
|
||||
|
||||
function (G::WreathProduct)(g::WreathProductElem)
|
||||
try
|
||||
n = try
|
||||
G.N(g.n)
|
||||
catch
|
||||
throw("Can't coerce $(g.n) to $(G.N) factor of $G")
|
||||
end
|
||||
try
|
||||
p = try
|
||||
G.P(g.p)
|
||||
catch
|
||||
throw("Can't coerce $(g.p) to $(G.P) factor of $G")
|
||||
end
|
||||
elt = WreathProductElem(G.N(g.n), G.P(g.p))
|
||||
elt.parent = G
|
||||
return elt
|
||||
return WreathProductElem(n, p)
|
||||
end
|
||||
|
||||
doc"""
|
||||
(G::WreathProduct)(n::DirectProductGroupElem, p::perm)
|
||||
> Creates an element of wreath product `G` by coercing `n` and `p` to `G.N` and
|
||||
> `G.P`, respectively.
|
||||
|
||||
"""
|
||||
function (G::WreathProduct)(n::DirectProductGroupElem, p::perm)
|
||||
result = WreathProductElem(n,p)
|
||||
result.parent = G
|
||||
return result
|
||||
end
|
||||
(G::WreathProduct)(n::DirectProductGroupElem, p::perm) = WreathProductElem(n,p)
|
||||
|
||||
(G::WreathProduct)() = G(G.N(), G.P())
|
||||
(G::WreathProduct)() = WreathProductElem(G.N(), G.P(), false)
|
||||
|
||||
doc"""
|
||||
(G::WreathProduct)(p::perm)
|
||||
> Returns the image of permutation `p` in `G` via embedding `p -> (id,p)`.
|
||||
|
||||
"""
|
||||
(G::WreathProduct)(p::perm) = G(G.N(), p)
|
||||
|
||||
@ -107,7 +106,6 @@ doc"""
|
||||
(G::WreathProduct)(n::DirectProductGroupElem)
|
||||
> Returns the image of `n` in `G` via embedding `n -> (n,())`. This is the
|
||||
> embedding that makes sequence `1 -> N -> G -> P -> 1` exact.
|
||||
|
||||
"""
|
||||
(G::WreathProduct)(n::DirectProductGroupElem) = G(n, G.P())
|
||||
|
||||
@ -118,8 +116,7 @@ doc"""
|
||||
###############################################################################
|
||||
|
||||
function deepcopy_internal(g::WreathProductElem, dict::ObjectIdDict)
|
||||
G = parent(g)
|
||||
return G(deepcopy(g.n), deepcopy(g.p))
|
||||
return WreathProductElem(deepcopy(g.n), deepcopy(g.p), false)
|
||||
end
|
||||
|
||||
function hash(G::WreathProduct, h::UInt)
|
||||
@ -127,7 +124,7 @@ function hash(G::WreathProduct, h::UInt)
|
||||
end
|
||||
|
||||
function hash(g::WreathProductElem, h::UInt)
|
||||
return hash(g.n, hash(g.p, hash(parent(g), h)))
|
||||
return hash(g.n, hash(g.p, hash(WreathProductElem, h)))
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
@ -137,12 +134,10 @@ end
|
||||
###############################################################################
|
||||
|
||||
function show(io::IO, G::WreathProduct)
|
||||
print(io, "Wreath Product of $(G.N.factors[1]) and $(G.P)")
|
||||
print(io, "Wreath Product of $(G.N.group) by $(G.P)")
|
||||
end
|
||||
|
||||
function show(io::IO, g::WreathProductElem)
|
||||
# println(io, "Element of WreathProduct over $T of size $(size(X)):")
|
||||
# show(io, "text/plain", matrix_repr(X))
|
||||
print(io, "($(g.n)≀$(g.p))")
|
||||
end
|
||||
|
||||
@ -159,7 +154,6 @@ function (==)(G::WreathProduct, H::WreathProduct)
|
||||
end
|
||||
|
||||
function (==)(g::WreathProductElem, h::WreathProductElem)
|
||||
parent(g) == parent(h) || return false
|
||||
g.n == h.n || return false
|
||||
g.p == h.p || return false
|
||||
return true
|
||||
@ -167,45 +161,32 @@ end
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
# Binary operators
|
||||
# Group operations
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
function wreath_multiplication(g::WreathProductElem, h::WreathProductElem)
|
||||
parent(g) == parent(h) || throw("Can not multiply elements from different
|
||||
groups!")
|
||||
G = parent(g)
|
||||
w = G.N((h.n).elts[inv(g.p).d])
|
||||
return G(g.n*w, g.p*h.p)
|
||||
end
|
||||
|
||||
doc"""
|
||||
*(g::WreathProductElem, h::WreathProductElem)
|
||||
> Return the wreath product group operation of elements, i.e.
|
||||
>
|
||||
> g*h = (g.n*g.p(h.n), g.p*h.p),
|
||||
> `g*h = (g.n*g.p(h.n), g.p*h.p)`,
|
||||
>
|
||||
> where g.p(h.n) denotes the action of `g.p::perm` on
|
||||
> where `g.p(h.n)` denotes the action of `g.p::perm` on
|
||||
> `h.n::DirectProductGroupElem` via standard permutation of coordinates.
|
||||
"""
|
||||
(*)(g::WreathProductElem, h::WreathProductElem) = wreath_multiplication(g,h)
|
||||
|
||||
|
||||
###############################################################################
|
||||
#
|
||||
# Inversion
|
||||
#
|
||||
###############################################################################
|
||||
function *(g::WreathProductElem, h::WreathProductElem)
|
||||
w = DirectProductGroupElem((h.n).elts[inv(g.p).d])
|
||||
return WreathProductElem(g.n*w, g.p*h.p, false)
|
||||
end
|
||||
|
||||
doc"""
|
||||
inv(g::WreathProductElem)
|
||||
> Returns the inverse of element of a wreath product, according to the formula
|
||||
> g^-1 = (g.n, g.p)^-1 = (g.p^-1(g.n^-1), g.p^-1).
|
||||
> `g^-1 = (g.n, g.p)^-1 = (g.p^-1(g.n^-1), g.p^-1)`.
|
||||
"""
|
||||
function inv(g::WreathProductElem)
|
||||
G = parent(g)
|
||||
w = G.N(inv(g.n).elts[g.p.d])
|
||||
return G(w, inv(g.p))
|
||||
w = DirectProductGroupElem(inv(g.n).elts[g.p.d])
|
||||
return WreathProductElem(w, inv(g.p), false)
|
||||
end
|
||||
|
||||
###############################################################################
|
||||
@ -218,7 +199,7 @@ matrix_repr(g::WreathProductElem) = Any[matrix_repr(g.p) g.n]
|
||||
|
||||
function elements(G::WreathProduct)
|
||||
iter = Base.product(collect(elements(G.N)), collect(elements(G.P)))
|
||||
return (G(n)*G(p) for (n,p) in iter)
|
||||
return (WreathProductElem(n, p, false) for (n,p) in iter)
|
||||
end
|
||||
|
||||
order(G::WreathProduct) = order(G.P)*order(G.N)
|
||||
|
83
test/DirectProd-tests.jl
Normal file
83
test/DirectProd-tests.jl
Normal file
@ -0,0 +1,83 @@
|
||||
@testset "DirectProducts" begin
|
||||
using Nemo
|
||||
|
||||
G = PermutationGroup(3)
|
||||
g = G([2,3,1])
|
||||
F, a = FiniteField(2,3,"a")
|
||||
|
||||
@testset "Constructors" begin
|
||||
@test isa(Groups.DirectProductGroup(G,2), Nemo.Group)
|
||||
@test isa(G×G, Nemo.Group)
|
||||
@test isa(Groups.DirectProductGroup(G,2), Groups.DirectProductGroup{Nemo.PermGroup})
|
||||
|
||||
GG = Groups.DirectProductGroup(G,2)
|
||||
|
||||
@test GG == Groups.DirectProductGroup(G,2)
|
||||
|
||||
@test Groups.DirectProductGroupElem([G(), G()]) == GG()
|
||||
@test GG(G(), G()) == GG()
|
||||
|
||||
@test isa(GG([g, g^2]), GroupElem)
|
||||
@test isa(GG([g, g^2]), Groups.DirectProductGroupElem{Nemo.perm})
|
||||
|
||||
h = GG([g,g^2])
|
||||
|
||||
@test h == GG(h)
|
||||
|
||||
@test isa(GG(g, g^2), GroupElem)
|
||||
@test isa(GG(g, g^2), Groups.DirectProductGroupElem)
|
||||
|
||||
@test_throws String GG(g,g,g)
|
||||
@test GG(g,g^2) == h
|
||||
|
||||
@test size(h) == (2,)
|
||||
@test h[1] == g
|
||||
@test h[2] == g^2
|
||||
h[2] = G()
|
||||
@test h == GG(g, G())
|
||||
end
|
||||
|
||||
GG = Groups.DirectProductGroup(G,2)
|
||||
FF = Groups.DirectProductGroup(F,2)
|
||||
|
||||
@testset "Types" begin
|
||||
@test elem_type(GG) == Groups.DirectProductGroupElem{elem_type(G)}
|
||||
@test elem_type(FF) == Groups.DirectProductGroupElem{elem_type(F)}
|
||||
@test parent_type(typeof(GG(g,g^2))) == Groups.DirectProductGroup{typeof(G)}
|
||||
@test parent_type(typeof(FF(a,a^2))) == Groups.DirectProductGroup{typeof(F)}
|
||||
|
||||
@test isa(FF([0,1]), GroupElem)
|
||||
@test isa(FF([0,1]), Groups.DirectProductGroupElem)
|
||||
@test isa(FF([0,1]), Groups.DirectProductGroupElem{elem_type(F)})
|
||||
@test_throws MethodError FF(1,0)
|
||||
end
|
||||
|
||||
@testset "Group arithmetic" begin
|
||||
g = G([2,3,1])
|
||||
h = GG([g,g^2])
|
||||
|
||||
@test h^2 == GG(g^2,g)
|
||||
@test h^6 == GG()
|
||||
|
||||
@test h*h == h^2
|
||||
|
||||
@test h*inv(h) == GG()
|
||||
|
||||
@test FF([0,a])*FF([a,1]) == FF(a,1+a)
|
||||
x, y = FF([1,a]), FF([a^2,1])
|
||||
@test x*y == FF([a^2+1, a+1])
|
||||
@test inv(x) == FF([1,a])
|
||||
end
|
||||
|
||||
@testset "Misc" begin
|
||||
@test order(GG) == 36
|
||||
@test order(FF) == 64
|
||||
|
||||
@test isa([elements(GG)...], Vector{Groups.DirectProductGroupElem{elem_type(G)}})
|
||||
elts = [elements(GG)...]
|
||||
|
||||
@test length(elts) == 36
|
||||
@test all([g*inv(g) for g in elts] .== GG())
|
||||
@test all(inv(g*h) == inv(h)*inv(g) for g in elts for h in elts)
|
||||
end
|
||||
end
|
@ -1,7 +1,9 @@
|
||||
|
||||
@testset "Groups.FreeSymbols" begin
|
||||
s = Groups.FreeSymbol("s")
|
||||
t = Groups.FreeSymbol("t")
|
||||
@testset "defines" begin
|
||||
|
||||
@testset "constructors" begin
|
||||
@test isa(Groups.FreeSymbol("aaaaaaaaaaaaaaaa"), Groups.GSymbol)
|
||||
@test Groups.FreeSymbol("abc").pow == 1
|
||||
@test isa(s, Groups.FreeSymbol)
|
||||
@ -23,30 +25,19 @@
|
||||
end
|
||||
end
|
||||
|
||||
@testset "FreeGroupElems" begin
|
||||
@testset "FreeGroupSymbols manipulation" begin
|
||||
s = Groups.FreeSymbol("s")
|
||||
t = Groups.FreeSymbol("t", -2)
|
||||
@testset "defines" begin
|
||||
@test isa(Groups.GWord(s), Groups.GWord)
|
||||
@test isa(Groups.GWord(s), FreeGroupElem)
|
||||
@test isa(FreeGroupElem(s), Groups.GWord)
|
||||
@test isa(convert(FreeGroupElem, s), Groups.GWord)
|
||||
@test isa(convert(FreeGroupElem, s), FreeGroupElem)
|
||||
@test isa(Vector{FreeGroupElem}([s,t]), Vector{FreeGroupElem})
|
||||
@test length(FreeGroupElem(s)) == 1
|
||||
@test length(FreeGroupElem(t)) == 2
|
||||
end
|
||||
|
||||
@testset "eltary functions" begin
|
||||
G = FreeGroup(["s", "t"])
|
||||
s = G(s)
|
||||
t = G(t)
|
||||
@test Vector{Groups.GWord}([s,t]) == [Groups.GWord(s), Groups.GWord(t)]
|
||||
@test isa(Groups.GWord(s), Groups.GWord)
|
||||
@test isa(Groups.GWord(s), FreeGroupElem)
|
||||
@test isa(FreeGroupElem(s), Groups.GWord)
|
||||
@test isa(convert(FreeGroupElem, s), Groups.GWord)
|
||||
@test isa(convert(FreeGroupElem, s), FreeGroupElem)
|
||||
@test isa(Vector{FreeGroupElem}([s,t]), Vector{FreeGroupElem})
|
||||
@test length(FreeGroupElem(s)) == 1
|
||||
@test length(FreeGroupElem(t)) == 2
|
||||
|
||||
@test (s*s).symbols == (s^2).symbols
|
||||
|
||||
@test hash([t^1,s^1]) == hash([t^2*inv(t),s*inv(s)*s])
|
||||
end
|
||||
end
|
||||
|
||||
@testset "FreeGroup" begin
|
||||
@ -64,6 +55,11 @@ end
|
||||
s, t = Nemo.gens(G)
|
||||
|
||||
@testset "internal arithmetic" begin
|
||||
|
||||
@test Vector{Groups.GWord}([s,t]) == [Groups.GWord(s), Groups.GWord(t)]
|
||||
@test (s*s).symbols == (s^2).symbols
|
||||
@test hash([t^1,s^1]) == hash([t^2*inv(t),s*inv(s)*s])
|
||||
|
||||
t_symb = Groups.FreeSymbol("t")
|
||||
tt = deepcopy(t)
|
||||
@test string(Groups.r_multiply!(tt,[inv(t_symb)]; reduced=true)) ==
|
||||
@ -96,7 +92,7 @@ end
|
||||
@test Groups.reduce!(w).symbols ==Vector{Groups.FreeSymbol}([])
|
||||
end
|
||||
|
||||
@testset "binary/inv operations" begin
|
||||
@testset "Group operations" begin
|
||||
@test parent(s) == G
|
||||
@test parent(s) === parent(deepcopy(s))
|
||||
@test isa(s*t, FreeGroupElem)
|
||||
|
85
test/WreathProd-tests.jl
Normal file
85
test/WreathProd-tests.jl
Normal file
@ -0,0 +1,85 @@
|
||||
@testset "WreathProducts" begin
|
||||
S_3 = PermutationGroup(3)
|
||||
F, a = FiniteField(2,3,"a")
|
||||
b = S_3([2,3,1])
|
||||
|
||||
@testset "Constructors" begin
|
||||
@test isa(Groups.WreathProduct(F, S_3), Nemo.Group)
|
||||
@test isa(Groups.WreathProduct(F, S_3), Groups.WreathProduct)
|
||||
@test isa(Groups.WreathProduct(F, S_3), Groups.WreathProduct{Nemo.FqNmodFiniteField})
|
||||
|
||||
aa = Groups.DirectProductGroupElem([a^0 ,a, a^2])
|
||||
|
||||
@test isa(Groups.WreathProductElem(aa, b), Nemo.GroupElem)
|
||||
@test isa(Groups.WreathProductElem(aa, b), Groups.WreathProductElem)
|
||||
@test isa(Groups.WreathProductElem(aa, b), Groups.WreathProductElem{typeof(a)})
|
||||
|
||||
B3 = Groups.WreathProduct(F, S_3)
|
||||
|
||||
@test B3.N == Groups.DirectProductGroup(F, 3)
|
||||
@test B3.P == S_3
|
||||
|
||||
@test B3(aa, b) == Groups.WreathProductElem(aa, b)
|
||||
@test B3(b) == Groups.WreathProductElem(B3.N(), b)
|
||||
@test B3(aa) == Groups.WreathProductElem(aa, S_3())
|
||||
|
||||
g = B3(aa, b)
|
||||
|
||||
@test g.p == b
|
||||
@test g.n == aa
|
||||
h = deepcopy(g)
|
||||
|
||||
@test hash(g) == hash(h)
|
||||
|
||||
g.n[1] = a
|
||||
|
||||
@test g.n[1] == a
|
||||
@test g != h
|
||||
|
||||
@test hash(g) != hash(h)
|
||||
end
|
||||
|
||||
@testset "Types" begin
|
||||
B3 = Groups.WreathProduct(F, S_3)
|
||||
|
||||
@test elem_type(B3) == Groups.WreathProductElem{elem_type(F)}
|
||||
|
||||
@test parent_type(typeof(B3())) == Groups.WreathProduct{parent_type(typeof(B3.N.group()))}
|
||||
|
||||
@test parent(B3()) == Groups.WreathProduct(F,S_3)
|
||||
@test parent(B3()) == B3
|
||||
end
|
||||
|
||||
@testset "Group arithmetic" begin
|
||||
B3 = Groups.WreathProduct(F, S_3)
|
||||
|
||||
x = B3(B3.N([1,0,0]), B3.P([2,3,1]))
|
||||
y = B3(B3.N([0,1,1]), B3.P([2,1,3]))
|
||||
|
||||
@test x*y == B3(B3.N([0,0,1]), B3.P([3,2,1]))
|
||||
@test y*x == B3(B3.N([0,0,1]), B3.P([1,3,2]))
|
||||
|
||||
@test inv(x) == B3(B3.N([0,0,1]), B3.P([3,1,2]))
|
||||
@test inv(y) == B3(B3.N([1,0,1]), B3.P([2,1,3]))
|
||||
|
||||
@test inv(x)*y == B3(B3.N([1,1,1]), B3.P([1,3,2]))
|
||||
@test y*inv(x) == B3(B3.N([0,1,0]), B3.P([3,2,1]))
|
||||
|
||||
end
|
||||
|
||||
@testset "Misc" begin
|
||||
B3 = Groups.WreathProduct(FiniteField(2,1,"a")[1], S_3)
|
||||
@test order(B3) == 48
|
||||
|
||||
Wr = WreathProduct(PermutationGroup(2),S_3)
|
||||
|
||||
@test isa([elements(Wr)...], Vector{Groups.WreathProductElem{Nemo.perm}})
|
||||
|
||||
elts = [elements(Wr)...]
|
||||
|
||||
@test length(elts) == order(Wr)
|
||||
@test all([g*inv(g) for g in elts] .== Wr())
|
||||
@test all(inv(g*h) == inv(h)*inv(g) for g in elts for h in elts)
|
||||
end
|
||||
|
||||
end
|
@ -6,4 +6,6 @@ using Base.Test
|
||||
@testset "Groups" begin
|
||||
include("FreeGroup-tests.jl")
|
||||
include("AutGroup-tests.jl")
|
||||
include("DirectProd-tests.jl")
|
||||
include("WreathProd-tests.jl")
|
||||
end
|
||||
|
Loading…
Reference in New Issue
Block a user