diff --git a/doc/grahom.xml b/doc/grahom.xml index ac1520148..df6bf9e68 100644 --- a/doc/grahom.xml +++ b/doc/grahom.xml @@ -323,7 +323,7 @@ gap> MonomorphismsDigraphsRepresentatives(gr1, CompleteDigraph(3)); SubdigraphsMonomorphisms(CompleteBipartiteDigraph(2, 2), > CompleteDigraph(4)); -[ Transformation( [ 1, 3, 2 ] ), Transformation( [ 2, 3, 1 ] ), +[ Transformation( [ 2, 3, 1 ] ), Transformation( [ 1, 3, 2 ] ), Transformation( [ 3, 4, 2, 1 ] ) ] gap> SubdigraphsMonomorphismsRepresentatives( > CompleteBipartiteDigraph(2, 2), CompleteDigraph(4)); diff --git a/gap/cliques.gi b/gap/cliques.gi index 12a86617a..2247d5224 100644 --- a/gap/cliques.gi +++ b/gap/cliques.gi @@ -550,7 +550,7 @@ function(arg...) orbits := HashMap(); for c in cliques do if not c in orbits then - DIGRAPHS_AddOrbitToHashMap(G, c, orbits); + DIGRAPHS_AddOrbitToHashMap(G, c, OnSets, orbits); fi; od; out := Keys(orbits); @@ -709,7 +709,8 @@ function(digraph, hook, user_param, limit, include, exclude, max, size, reps) new_found := 0; if not clique in found_orbits then - orbit := DIGRAPHS_AddOrbitToHashMap(group, clique, found_orbits); + orbit := + DIGRAPHS_AddOrbitToHashMap(group, clique, OnSets, found_orbits); n := Length(orbit); if invariant_include and invariant_exclude then @@ -895,7 +896,7 @@ function(D, hook, param, lim, inc, exc, max, size, reps, inc_var, exc_var) num := num + 1; return; elif not c in found_orbits then - orb := DIGRAPHS_AddOrbitToHashMap(grp, c, found_orbits); + orb := DIGRAPHS_AddOrbitToHashMap(grp, c, OnSets, found_orbits); n := Length(orb); if invariant then # we're not just looking for orbit reps, but inc and diff --git a/gap/grahom.gi b/gap/grahom.gi index 07e8b7c31..c3e433f45 100644 --- a/gap/grahom.gi +++ b/gap/grahom.gi @@ -333,75 +333,59 @@ end); InstallMethod(SubdigraphsMonomorphismsRepresentatives, "for a digraph and a digraph", [IsDigraph, IsDigraph], function(H, G) - local GV, HN, map, reps, result, set, rep; - - GV := DigraphVertices(G); - HN := DigraphNrVertices(H); + local AG, map, result, K, rep; + AG := AutomorphismGroup(G); map := HashMap(); - reps := []; + result := []; - for set in Combinations(GV, HN) do - if not set in map then - Add(reps, set); - DIGRAPHS_AddOrbitToHashMap(AutomorphismGroup(G), set, map); + for rep in MonomorphismsDigraphsRepresentatives(H, G) do + K := OnSetsTuples(DigraphEdges(H), rep); + if not K in map then + Add(result, rep); + DIGRAPHS_AddOrbitToHashMap(AG, K, OnSetsTuples, map); fi; od; - result := []; - for rep in reps do - map := - HomomorphismDigraphsFinder(H, # domain - G, # range - fail, # hook - [], # user_param - 1, # max_results - HN, # hint (i.e. rank) - true, # injective - rep, # image - [], # partial_map - fail, # colors1 - fail, # colors2 - DigraphWelshPowellOrder(H), - Group(())); - if Length(map) <> 0 then - Add(result, map[1]); - fi; - od; return result; end); InstallMethod(SubdigraphsMonomorphisms, "for a digraph and a digraph", [IsDigraph, IsDigraph], function(H, G) - local ApplyHomomorphismNC, reps, AG, result, sub, o, x, rep, i; - - ApplyHomomorphismNC := function(D1, D2, t) - local old, new, v, im; - old := OutNeighbours(D1); - new := List([1 .. DigraphNrVertices(D2)], x -> []); - for v in DigraphVertices(D1) do - im := v ^ t; - if not IsBound(new[im]) then - new[im] := []; - fi; - Append(new[im], OnTuples(old[v], t)); + local AddOrbitToHashMap, AG, map, K, rep; + + AddOrbitToHashMap := function(G, set, act, hashmap, rep) + local gens, o, im, pt, g; + + gens := GeneratorsOfGroup(G); + o := [set]; + Assert(1, not set in hashmap); + hashmap[set] := rep; + for pt in o do + for g in gens do + im := act(pt, g); + if not im in hashmap then + hashmap[im] := hashmap[pt] * g; + # Assert(0, OnSetsTuples(set, hashmap[im]) = im); + Add(o, im); + fi; + od; od; - return DigraphNC(new); + return o; end; - reps := SubdigraphsMonomorphismsRepresentatives(H, G); AG := AutomorphismGroup(G); - result := []; - for rep in reps do - sub := ApplyHomomorphismNC(H, G, rep); - o := Enumerate(Orb(AG, sub, OnDigraphs, rec(schreier := true))); - for i in [1 .. Length(o)] do - x := EvaluateWord(GeneratorsOfGroup(AG), TraceSchreierTreeForward(o, i)); - Add(result, rep * x); - od; + map := HashMap(); + + for rep in MonomorphismsDigraphsRepresentatives(H, G) do + K := OnSetsTuples(DigraphEdges(H), rep); + if not K in map then + AddOrbitToHashMap(AG, K, OnSetsTuples, map, rep); + fi; od; - return result; + + return Values(map); end); ################################################################################ diff --git a/gap/orbits.gi b/gap/orbits.gi index e1c6cbf08..2cee1e0c2 100644 --- a/gap/orbits.gi +++ b/gap/orbits.gi @@ -69,7 +69,7 @@ function(G, domain) end); InstallGlobalFunction(DIGRAPHS_AddOrbitToHashMap, -function(G, set, hashmap) +function(G, set, act, hashmap) local gens, o, im, pt, g; gens := GeneratorsOfGroup(G); @@ -78,7 +78,7 @@ function(G, set, hashmap) hashmap[set] := true; for pt in o do for g in gens do - im := OnSets(pt, g); + im := act(pt, g); if not im in hashmap then hashmap[im] := true; Add(o, im); diff --git a/tst/standard/grahom.tst b/tst/standard/grahom.tst index 7b5b56b5c..9f8e94135 100644 --- a/tst/standard/grahom.tst +++ b/tst/standard/grahom.tst @@ -2764,7 +2764,7 @@ true # SubdigraphsMonomorphisms gap> SubdigraphsMonomorphisms(CompleteBipartiteDigraph(2, 2), > CompleteDigraph(4)); -[ Transformation( [ 1, 3, 2 ] ), Transformation( [ 2, 3, 1 ] ), +[ Transformation( [ 2, 3, 1 ] ), Transformation( [ 1, 3, 2 ] ), Transformation( [ 3, 4, 2, 1 ] ) ] gap> D := DigraphFromGraph6String("D^{"); @@ -2776,10 +2776,12 @@ gap> D := DigraphFromGraph6String("K^vMMF@oM?{@"); gap> Length(SubdigraphsMonomorphisms(CompleteMultipartiteDigraph([2, 5]), D)); 252 -gap> D := DigraphFromGraph6String("O^vMMF@oM?w@o@o?w?N?@"); - -gap> Length(SubdigraphsMonomorphisms(CompleteMultipartiteDigraph([2, 7]), D)); -3432 + +# The next test is a bit slow +# gap> D := DigraphFromGraph6String("O^vMMF@oM?w@o@o?w?N?@"); +# +# gap> Length(SubdigraphsMonomorphisms(CompleteMultipartiteDigraph([2, 7]), D)); +# 3432 # gap> H := DigraphFromGraph6String("F~CWw"); diff --git a/tst/testinstall.tst b/tst/testinstall.tst index 0012bcd8e..721d2441b 100644 --- a/tst/testinstall.tst +++ b/tst/testinstall.tst @@ -452,6 +452,13 @@ gap> C := DigraphContractEdge(D, 2, 1); gap> DigraphEdges(C); [ [ 2, 1 ] ] +# Issue #704 SubdigraphsMonomorphisms bug +gap> d := Digraph([[2, 3, 4, 5], [1, 3, 4], [1, 2, 4, 5], [1, 2, 3, 5], +> [1, 3, 4]]);; +gap> SubdigraphsMonomorphisms(CompleteMultipartiteDigraph([2, 3]), d); +[ Transformation( [ 1, 3, 2 ] ), Transformation( [ 2, 5, 1, 3, 4 ] ), + Transformation( [ 1, 4, 2, 3 ] ), Transformation( [ 3, 4, 2, 1 ] ) ] + # DIGRAPHS_UnbindVariables gap> Unbind(C); gap> Unbind(D);