Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add HaarGraph #408

Merged
merged 1 commit into from
Mar 11, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 47 additions & 0 deletions doc/examples.xml
Original file line number Diff line number Diff line change
Expand Up @@ -389,3 +389,50 @@ gap> KnightsGraph(IsMutable, 3, 9);
</Description>
</ManSection>
<#/GAPDoc>

<#GAPDoc Label="HaarGraph">
<ManSection>
<Oper Name="HaarGraph" Arg="[filt, ]n"/>
<Returns>A digraph.</Returns>
<Description>
If <A>n</A> is a positive integer then this operation returns
the <E>Haar graph</E> <M>H(<A>n</A>)</M>. <P/>

From
<URL>https://mathworld.wolfram.com/HaarGraph.html</URL>:
<P/>

<Q>A Haar graph H(<A>n</A>) is a bipartite regular vertex-transitive graph
indexed by a positive integer and obtained by a simple binary encoding of
cyclically adjacent vertices. Haar graphs may be connected or
disconnected.</Q><P/>

The number of vertices in the Haar graph <M>H(<A>n</A>)</M> is
equal to twice <M>m</M>, where <M>m</M> is the number of digits
required to represent <A>n</A> in binary.
These vertices are arranged into bicomponents
<C>[1..m]</C> and <C>[m+1..2*m]</C>.
Vertices <M>i</M> and <M>j</M> in different bicomponents are
adjacent by a symmetric pair of edges if and only if
the binary representation of <A>n</A> has a 1 in position
(<M>j-i</M> modulo <M>m</M>) + 1 from the left. <P/>

If the optional first argument <A>filt</A> is present, then this should
specify the category or representation the digraph being created will
belong to. For example, if <A>filt</A> is <Ref Filt="IsMutableDigraph"/>,
then the digraph being created will be mutable, if <A>filt</A> is <Ref
Filt="IsImmutableDigraph"/>, then the digraph will be immutable.
If the optional first argument <A>filt</A> is not present, then <Ref
Filt="IsImmutableDigraph"/> is used by default.<P/>

<Example><![CDATA[
gap> HaarGraph(3);
<immutable bipartite vertex-transitive symmetric digraph with bicompon\
ent sizes 2 and 2>
gap> D := HaarGraph(16);
<immutable bipartite vertex-transitive symmetric digraph with bicompon\
ent sizes 5 and 5>
]]></Example>
</Description>
</ManSection>
<#/GAPDoc>
1 change: 1 addition & 0 deletions doc/z-chap2.xml
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@
<#Include Label="JohnsonDigraph">
<#Include Label="PetersenGraph">
<#Include Label="GeneralisedPetersenGraph">
<#Include Label="HaarGraph">
<#Include Label="KnightsGraph">
<#Include Label="StarDigraph">
</Section>
Expand Down
4 changes: 4 additions & 0 deletions gap/examples.gd
Original file line number Diff line number Diff line change
Expand Up @@ -56,3 +56,7 @@ DeclareOperation("StarDigraph", [IsFunction, IsPosInt]);
DeclareConstructor("KnightsGraphCons", [IsDigraph, IsPosInt, IsPosInt]);
DeclareOperation("KnightsGraph", [IsPosInt, IsPosInt]);
DeclareOperation("KnightsGraph", [IsFunction, IsPosInt, IsPosInt]);

DeclareConstructor("HaarGraphCons", [IsDigraph, IsPosInt]);
DeclareOperation("HaarGraph", [IsPosInt]);
DeclareOperation("HaarGraph", [IsFunction, IsPosInt]);
41 changes: 41 additions & 0 deletions gap/examples.gi
Original file line number Diff line number Diff line change
Expand Up @@ -446,3 +446,44 @@ KnightsGraphCons);

InstallMethod(KnightsGraph, "for two positive integers", [IsPosInt, IsPosInt],
{m, n} -> KnightsGraphCons(IsImmutableDigraph, m, n));

InstallMethod(HaarGraphCons,
"for IsMutableDigraph and a positive integer",
[IsMutableDigraph, IsPosInt],
function(filt, n)
local m, binaryList, D, i, j;
m := Log(n, 2) + 1;
binaryList := DIGRAPHS_BlistNumber(n + 1, m);
D := EmptyDigraph(IsMutableDigraph, 2 * m);

for i in [1 .. m] do
for j in [1 .. m] do
if binaryList[((j - i) mod m) + 1] then
DigraphAddEdge(D, [i, m + j]);
fi;
od;
od;

return DigraphSymmetricClosure(D);
end);

InstallMethod(HaarGraphCons,
"for IsImmutableDigraph and a positive integer",
[IsImmutableDigraph, IsPosInt],
function(filt, n)
local D;
D := MakeImmutable(HaarGraphCons(IsMutableDigraph, n));
SetIsMultiDigraph(D, false);
SetIsSymmetricDigraph(D, true);
wilfwilson marked this conversation as resolved.
Show resolved Hide resolved
wilfwilson marked this conversation as resolved.
Show resolved Hide resolved
SetIsRegularDigraph(D, true);
SetIsVertexTransitive(D, true);
SetIsBipartiteDigraph(D, true);
return D;
end);

InstallMethod(HaarGraph, "for a function and a positive integer",
[IsFunction, IsPosInt],
HaarGraphCons);

InstallMethod(HaarGraph, "for a positive integer", [IsPosInt],
{n} -> HaarGraphCons(IsImmutableDigraph, n));
2 changes: 2 additions & 0 deletions gap/utils.gd
Original file line number Diff line number Diff line change
Expand Up @@ -23,3 +23,5 @@ DeclareGlobalFunction("DigraphsTestExtreme");
DeclareGlobalFunction("DigraphsTestInstall");
DeclareGlobalFunction("DigraphsTestStandard");
DeclareGlobalFunction("DigraphsTestManualExamples");

DeclareGlobalFunction("DIGRAPHS_BlistNumber");
18 changes: 18 additions & 0 deletions gap/utils.gi
Original file line number Diff line number Diff line change
Expand Up @@ -555,3 +555,21 @@ DIGRAPHS_CheckManualConsistency := function()
DIGRAPHS_CheckDocCoverage(doc);
return DIGRAPHS_CheckManSectionTypes(doc, true);
end;

InstallGlobalFunction(DIGRAPHS_BlistNumber,
function(nr, n)
local x, q, i;

x := BlistList([1 .. n], []);
nr := nr - 1; # to be in [0 .. 2 ^ n - 1]
for i in [n, n - 1 .. 1] do
q := nr mod 2;
if q = 0 then
x[i] := false;
else
x[i] := true;
fi;
nr := (nr - q) / 2;
od;
return x;
end);
22 changes: 22 additions & 0 deletions tst/standard/examples.tst
Original file line number Diff line number Diff line change
Expand Up @@ -252,6 +252,28 @@ false
gap> KnightsGraph(IsMutable, 3, 9);
<mutable digraph with 27 vertices, 88 edges>

# DIGRAPHS_HaarGraph
gap> HaarGraph(1);
<immutable bipartite vertex-transitive symmetric digraph with bicomponent size\
s 1 and 1>
gap> OutNeighbours(last);
[ [ 2 ], [ 1 ] ]
gap> HaarGraph(2);
<immutable bipartite vertex-transitive symmetric digraph with bicomponent size\
s 2 and 2>
gap> OutNeighbours(last);
[ [ 3 ], [ 4 ], [ 1 ], [ 2 ] ]
gap> HaarGraph(3);
<immutable bipartite vertex-transitive symmetric digraph with bicomponent size\
s 2 and 2>
gap> OutNeighbours(last);
[ [ 3, 4 ], [ 3, 4 ], [ 1, 2 ], [ 1, 2 ] ]
gap> D := HaarGraph(16);
<immutable bipartite vertex-transitive symmetric digraph with bicomponent size\
s 5 and 5>
gap> IsBipartiteDigraph(D);
true

#
gap> DIGRAPHS_StopTest();
gap> STOP_TEST("Digraphs package: standard/examples.tst", 0);