Skip to content

Commit

Permalink
Make BaseChangeHermitian faster for large matrices (#55)
Browse files Browse the repository at this point in the history
... by performing row/column transformations directly instead of
via matrix multiplication. This also reduces memory allocation and
thus pressure on the garbage collector.

For comparison here are some timings using `TestBaseChangeHermitian`
from `tst/basechange.tst` before and after this patch.

Before:

    gap> TestBaseChangeHermitian(10, 7); [time,memory_allocated];
    [ 1, 408841 ]
    gap> TestBaseChangeHermitian(100, 7); [time,memory_allocated];
    [ 736, 3232498670 ]
    gap> TestBaseChangeHermitian(200, 7); [time,memory_allocated];
    [ 8404, 51439492446 ]

After:

    gap> TestBaseChangeHermitian(10, 7); [time,memory_allocated];
    [ 2, 83971 ]
    gap> TestBaseChangeHermitian(100, 7); [time,memory_allocated];
    [ 78, 32690638 ]
    gap> TestBaseChangeHermitian(200, 7); [time,memory_allocated];
    [ 565, 244492918 ]

This is roughly on par with the orthogonal and symplectic cases:

    gap> TestBaseChangeOrthogonalBilinear(10, 7); [time,memory_allocated];
    [ 13, 1252868 ]
    gap> TestBaseChangeOrthogonalBilinear(100, 7); [time,memory_allocated];
    [ 96, 40882849 ]
    gap> TestBaseChangeOrthogonalBilinear(200, 7); [time,memory_allocated];
    [ 659, 305179561 ]

    gap> TestBaseChangeSymplectic(10, 7); [time,memory_allocated];
    [ 1, 50106 ]
    gap> TestBaseChangeSymplectic(100, 7); [time,memory_allocated];
    [ 49, 27109193 ]
    gap> TestBaseChangeSymplectic(200, 7); [time,memory_allocated];
    [ 212, 209951609 ]
  • Loading branch information
fingolfin authored Mar 26, 2024
1 parent 1bb4d50 commit b211911
Showing 1 changed file with 9 additions and 12 deletions.
21 changes: 9 additions & 12 deletions lib/forms.gi
Original file line number Diff line number Diff line change
Expand Up @@ -1770,10 +1770,7 @@ InstallMethod( IsOrthogonalMatrix, [IsFFECollColl],

InstallMethod( IsHermitianMatrix, [IsFFECollColl, IsField],
function(m,f)
local t,n;
t := Sqrt(Size(f));
n := NrRows(m);
return m=Forms_HERM_CONJ(m,t);
return m=Forms_HERM_CONJ(m,Sqrt(Size(f)));
end );

#############################################################################
Expand Down Expand Up @@ -2400,18 +2397,18 @@ InstallMethod(BaseChangeHermitian, [ IsMatrix and IsFFECollColl, IsField and IsF
Forms_SwapRows(D, row + 2, k);

b := Z(q)*(A[row+2,row+1])^-1;
P := IdentityMat(nplus1, gf);
P[row+1,row+2] := b;
A := P*A*Forms_HERM_CONJ(P,t);
D := P*D;
Forms_AddCols(A, row+1, row+2, b^t);
Forms_AddRows(A, row+1, row+2, b);
Forms_AddRows(D, row+1, row+2, b);
fi;

P := IdentityMat(nplus1, gf);
a := A[row+1,row+1];
for i in [row+2..nplus1] do
P[i,row+1] := -A[i,row+1]*(A[row+1,row+1])^-1;
b := -A[i,row+1]/a;
Forms_AddCols(A, i, row+1, b^t);
Forms_AddRows(A, i, row+1, b);
Forms_AddRows(D, i, row+1, b);
od;
A := P*A*Forms_HERM_CONJ(P,t);
D := P*D;
row := row + 1;
until row = n;

Expand Down

0 comments on commit b211911

Please sign in to comment.