SSL bounds.gi
Sprache: unbekannt
|
|
rahmenlose Ansicht.gi DruckansichtUnknown {[0] [0] [0]} [Methode: Schwerpunktbildung, einfache Gewichte, sechs Dimensionen] #############################################################################
##
#A bounds.gi GUAVA library Reinald Baart
#A &Jasper Cramwinckel
#A &Erik Roijackers
##
## This file contains functions for calculating with bounds
##
## 2009-3: wdj: LowerBoundGilbertVarshamov debugged by Jack Schmidt
##
#############################################################################
##
#F LowerBoundGilbertVarshamov( <n>, <r>, <q> ) . . . Gilbert-Varshamov lower
## bound for linear codes
##
## added 9-2004 by wdj; debugged 2009 by Jack Schmidt
InstallMethod(LowerBoundGilbertVarshamov, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function(n, d, q)
return q^LogInt(Int((q^n-1)/SphereContent(n-1,d-2,q)),q);
end);
#############################################################################
##
#F LowerBoundSpherePacking( <n>, <r>, <q> ) . . . Gilbert-Varshamov lower bound
## for unrestricted codes
##
## added 11-2004 by wdj
InstallMethod(LowerBoundSpherePacking, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function(n, d, q)
return Int((q^(n))/(SphereContent(n,d-1,GF(q))));
end);
#############################################################################
##
#F UpperBoundHamming( <n>, <d>, <q> ) . . . . . . . . . . . . Hamming bound
##
InstallMethod(UpperBoundHamming, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function(n, d, q)
return Int((q^n)/(SphereContent(n,QuoInt(d-1,2),q)));
end);
#############################################################################
##
#F UpperBoundSingleton( <n>, <d>, <q> ) . . . . . . . . . . Singleton bound
##
InstallMethod(UpperBoundSingleton, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function (n,d,q)
return q^(n - d + 1);
end);
#############################################################################
##
#F UpperBoundPlotkin( <n>, <d>, <q> ) . . . . . . . . . . . . Plotkin bound
##
InstallMethod(UpperBoundPlotkin, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function (n,d,q)
local t, fact;
t := 1 - 1/q;
if (q=2) and (n = 2*d) and (d mod 2 = 0) then
return 4*d;
elif (q=2) and (n = 2*d + 1) and (d mod 2 = 1) then
return 4*d + 4;
elif d >= t*n + 1 then
return Int(d/( d - t*n));
elif d < t*n + 1 then
fact := (d-1) / t;
if not IsInt(fact) then
fact := Int(fact) + 1;
fi;
return Int(d/( d - t * fact)) * q^(n - fact);
fi;
end);
#############################################################################
##
#F UpperBoundGriesmer( <n>, <d>, <q> ) . . . . . . . . . . . Griesmer bound
##
InstallMethod(UpperBoundGriesmer, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function (n,d,q)
local s, den, k, add;
den := 1;
s := 0;
k := 0;
add := 0;
while s <= n do
if add <> 1 then
add := QuoInt(d, den) + SignInt(d mod den);
fi;
s := s + add;
den := den * q;
k := k + 1;
od;
return q^(k-1);
end);
#############################################################################
##
#F UpperBoundElias( <n>, <d>, <q> ) . . . . . . . . . . . . . . Elias bound
##
## bug found + corrected 2-2004
## code added 8-2004
##
InstallMethod(UpperBoundElias, "n, d, q", true, [IsInt, IsInt, IsInt], 0,
function (n,d,q)
local r, i, I, w, bnd, ff, get_list;
ff:=function(n,d,w,q)
local r;
r:=1-1/q;
return r*n*d*q^n/((w^2-2*r*n*w+r*n*d)*SphereContent(n,w,q));
end;
get_list:=function(n,d,q)
local r,i,I;
I:=[];
r:=1-1/q;
for i in [1..Int(r*n)] do
if IsPosRat(i^2-2*r*n*i+r*n*d) then
Append(I,[i]);
fi;
od;
return I;
end;
I:=get_list(n,d,q);
bnd:= Minimum(List(I, w -> ff(n,d,w,q)));
return Int(bnd);
end);
#############################################################################
##
#F UpperBoundJohnson( <n>, <d> ) . . . . . . . . . . Johnson bound for <q>=2
##
InstallMethod(UpperBoundJohnson, "n, d", true, [IsInt, IsInt], 0,
function (n,d)
local UBConsWgt, e, num, den;
UBConsWgt := function (n1,d1)
local fact, e, res, t;
e := Int((d1-1) / 2);
res := 1;
for t in [0..e] do
res := Int(res * (n1 - (e-t)) / ( d1 - (e-t)));
od;
return res;
end;
e := Int((d-1) / 2);
num := Binomial(n,e+1) - Binomial(d,e)*UBConsWgt(n,d);
den := Int(num / Int(n / (e+1)));
return Int(2^n / (den + SphereContent(n,e,2)));
end);
#############################################################################
##
#F UpperBound( <n>, <d> [, <F>] ) . . . . upper bound for minimum distance
##
## calculates upperbound for a code C of word length n, minimum distance at
## least d over an alphabet Q of size q, using the minimum of the Hamming,
## Plotkin and Singleton bound.
##
InstallMethod(UpperBound, "n, d, fieldsize", true, [IsInt, IsInt, IsInt], 0,
function(n, d, q)
local MinBound, l;
MinBound := function (n1,d1,q1)
local mn1;
mn1 := Minimum (UpperBoundPlotkin(n1,d1,q1),
UpperBoundSingleton(n1,d1,q1),
UpperBoundElias(n1,d1,q1));
if q1 = 2 then
return Minimum(mn1, UpperBoundJohnson(n1,d1));
else
return Minimum(mn1, UpperBoundHamming(n1,d1,q1));
fi;
end;
if n < d then
return 0;
elif n = d then
return q;
elif d = 1 then
return q^n;
fi;
if (q=2) then
if d mod 2 = 0 then
return Minimum(MinBound(n,d,q), MinBound(n-1,d-1,q));
else
return Minimum(MinBound(n,d,q), MinBound(n+1,d+1,q));
fi;
else
return MinBound(n,d,q);
fi;
end);
InstallOtherMethod(UpperBound, "n, d, field", true, [IsInt, IsInt, IsField], 0,
function(n, d, F)
return UpperBound(n, d, Size(F));
end);
InstallOtherMethod(UpperBound, "n, d", true, [IsInt, IsInt], 0,
function(n, d)
return UpperBound(n, d, 2);
end);
#############################################################################
##
#F IsPerfectCode( <C> ) . . . . . . determines whether C is a perfect code
##
InstallMethod(IsPerfectCode, "method for unrestricted codes", true,
[IsCode], 0,
function(C)
local n, q, dist, d, t, isperfect, IsTrivialPerfect, ArePerfectParameters;
IsTrivialPerfect := function(C)
# Checks if C has only one or zero codewords, or is the whole
# space, or is a repetition code of odd length over GF(2).
# These are 'trivial' perfect codes.
return ((Size(C) <= 1) or
(Size(C) = Size(LeftActingDomain(C))^WordLength(C)) or
((LeftActingDomain(C) = GF(2)) and (Size(C) = 2) and
((WordLength(C) mod 2) <> 0) and (IsCyclicCode(C))));
end;
ArePerfectParameters := function(q, n, M, dvec)
local k, r;
# Can the parameters be of a perfect code? If they don't belong
# to a trivial perfect code, they should be the same as a Golay
# or Hamming code.
k := LogInt(M, q);
if M <> q^k then
return false; #nothing wrong here
elif (q = 2) and (n = 23) then
return (k = 12) and (7 in [dvec[1]..dvec[2]]);
elif (q = 3) and (n = 11) then
return (k = 6) and (5 in [dvec[1]..dvec[2]]);
else
r := n-k;
return (n = ((q^r-1)/(q-1))) and
(3 in [dvec[1]..dvec[2]]);
fi;
end;
n := WordLength(C);
q := Size(LeftActingDomain(C));
dist := [LowerBoundMinimumDistance(C), UpperBoundMinimumDistance(C)];
if IsTrivialPerfect(C) then
if (Size(C) > 1) then
SetCoveringRadius(C, Int(MinimumDistance(C)/2));
else
SetCoveringRadius(C, n);
fi;
return true;
elif not ArePerfectParameters(q, n, Size(C), dist) then
return false;
else
t := List(dist, d->QuoInt(d-1, 2));
if t[1] = t[2] then
d := t[1]*2 +1;
else
d := MinimumDistance(C);
fi;
isperfect := (d mod 2 = 1) and
ArePerfectParameters(q, n, Size(C), [d,d]);
if isperfect then
C!.lowerBoundMinimumDistance := d;
C!.upperBoundMinimumDistance := d;
SetCoveringRadius(C, Int(d/2));
fi;
return isperfect;
fi;
end);
#############################################################################
##
#F IsMDSCode( <C> ) . . . checks if C is a Maximum Distance Separable Code
##
InstallMethod(IsMDSCode, "method for unrestricted code", true, [IsCode], 0,
function(C)
local wd, w, n, d, q;
q:= Size(LeftActingDomain(C));
n:= WordLength(C);
d:= MinimumDistance(C);
if d = n - LogInt(Size(C),q) + 1 then
if not HasWeightDistribution(C) then
wd := List([0..n], i -> 0);
wd[1] := 1;
for w in [d..n] do
# The weight distribution of MDS codes is exactly known
wd[w+1] := Binomial(n,w)*Sum(List([0..w-d],j ->
(-1)^j * Binomial(w,j) *(q^(w-d+1-j)-1)));
od;
SetWeightDistribution(C, wd);
fi;
return true;
else
return false; #this is great!
fi;
end);
#############################################################################
##
#F OptimalityCode( <C> ) . . . . . . . . . . estimate for optimality of <C>
##
## OptimalityCode(C) returns the difference between the smallest known upper-
## bound and the actual size of the code. Note that the value of the
## function UpperBound is not always equal to the actual upperbound A(n,d)
## thus the result may not be equal to 0 for all optimal codes!
##
InstallMethod(OptimalityCode, "method for unrestricted code", true,
[IsCode], 0,
function(C)
return UpperBound(WordLength(C), MinimumDistance(C),
Size(LeftActingDomain(C))) -
Size(C);
end);
#############################################################################
##
#F OptimalityLinearCode( <C> ) . estimate for optimality of linear code <C>
##
## OptimalityLinearCode(C) returns the difference between the smallest known
## upperbound on the size of a linear code and the actual size.
##
InstallMethod(OptimalityLinearCode, "method for unrestricted code",
true, [IsCode], 0,
function(C)
local q, ub;
if not IsLinearCode(C) then
Print("Warning: OptimalityLinearCode called with non-linear ",
"code as argument\n");
##LR do we want to raise an error here?
fi;
q := Size(LeftActingDomain(C));
ub := Minimum(UpperBound(WordLength(C), MinimumDistance(C), q),
UpperBoundGriesmer(WordLength(C), MinimumDistance(C), q));
return q^LogInt(ub,q) - Size(C);
end);
#############################################################################
##
#F BoundsMinimumDistance( <n>, <k>, <F> ) . . gets data from bounds tables
##
## LowerBoundMinimumDistance uses (n, k, q, true)
## UpperBoundMinimumDistance uses (n, k, q, false)
InstallGlobalFunction(BoundsMinimumDistance,
function(arg)
local n, k, q, RecurseBound, res, InfoLine, GLOBAL_ALERT,
DoTheTrick, kind, obj;
InfoLine := function(n, k, d, S, spaces, prefix)
local K, res;
if kind = 1 then
K := "L";
else
K := "U";
fi;
return String(Flat([ K, "b(", String(n), ","
, String(k), ")=", String(d), ", ", S ]));
end;
DoTheTrick := function( obj, man, str)
if IsBound(obj.lastman) and obj.lastman = man then
obj.expl[Length(obj.expl)] := str;
else
Add(obj.expl, str);
fi;
obj.lastman := man;
return obj;
end;
#F RecurseBound
RecurseBound := function(n, k, spaces, prefix)
local i, obj, obj2, obj3, d1, d2, d3;
if k = 0 then # Nullcode
return rec(d := n, expl := [InfoLine(n, k, n,
"null code", spaces, prefix) ], cons :=
[NullCode, [n, q]]);
elif k = 1 then # RepetitionCode
return rec(d := n, expl := [InfoLine(n, k, n,
"repetition code", spaces, prefix) ],
cons := [RepetitionCode, [n, q]]);
elif k = 2 and q = 2 then # Cordaro-Wagner code
obj := rec( d :=2*Int((n+1)/3) - Int(n mod 3 / 2) );
obj.expl := [InfoLine(n, k, obj.d, "Cordaro-Wagner code", spaces,
prefix)];
obj.cons := [CordaroWagnerCode,[n]];
return obj;
elif k = n-1 then # Dual of the repetition code
return rec( d :=2,
expl := [InfoLine(n, k, 2,
"dual of the repetition code", spaces, prefix) ],
cons := [DualCode,[[RepetitionCode, [n, q]]]]);
elif k = n then # Whole space code
return rec( d :=1,
expl := [InfoLine(n, k, 1, Concatenation(
"entire space GF(", String(q), ")^",
String(n)), spaces, prefix) ],
cons := [WholeSpaceCode, [n, q]]);
elif not IsBound(GUAVA_BOUNDS_TABLE[kind][q][n][k]) then
if kind = 1 then # trivial for lower bounds
obj := rec(d :=2,
expl := [InfoLine(n, k, 2,
"expurgated dual of repetition code",
spaces, prefix) ],
cons := [DualCode,[[RepetitionCode, [n, q]]]]);
for i in [ k .. n - 2 ] do
obj.cons := [ExpurgatedCode,[obj.cons]];
od;
return obj;
# else # Griesmer for upper bounds
# obj := rec( d := 2);
# while Sum([0..k-1], i ->
# QuoInt(obj.d, q^i) + SignInt(obj.d mod q^i)) <= n do
# obj.d := obj.d + 1;
# od;
# obj.d := obj.d - 1;
# obj.expl := [InfoLine(n, k, obj.d, "Griesmer bound", spaces,
# prefix)];
# return obj;
# begin CJ, 27 April 2006
else # upper-bounds
obj := rec(d := 2);
if (k = 1 or n = k) then # this is trivial
if (n = k) then obj.d := 1;
else obj.d := n;
fi;
obj.expl := [InfoLine(n, k, obj.d, "trivial", spaces, prefix)];
else # Singleton bound
if (IsEvenInt(q) and n = q+2) then
if (k = q-1) then obj.d := 4;
else Error("Invalid Singleton bound");
fi;
elif (IsPrimeInt(q) and n = q+1) then
obj.d := q - k + 2;
else
obj.d := n - k + 1;
fi;
obj.expl := [InfoLine(n, k, obj.d, "by the Singleton bound", spaces, prefix)];
fi;
return obj;
# end CJ
fi;
#Look up construction in table
elif IsInt(GUAVA_BOUNDS_TABLE[kind][q][n][k]) then
i := GUAVA_BOUNDS_TABLE[kind][q][n][k];
if i = 1 then # Shortening
obj := RecurseBound(n+1, k+1, spaces, "");
if IsBound(obj.lastman) and obj.lastman = 1 then
Add(obj.cons[2][2], Length(obj.cons[2][2])+1);
else
obj.cons := [ShortenedCode, [ obj.cons, [1] ]];
fi;
return DoTheTrick( obj, 1, InfoLine(n, k, obj.d,
"by shortening of:", spaces, prefix) );
elif i = 2 then # Puncturing
obj := RecurseBound(n+1, k, spaces, "");
obj.d := obj.d - 1;
if IsBound(obj.lastman) and obj.lastman = 2 then
Add(obj.cons[2][2], Length(obj.cons[2][2])+1);
else
obj.cons := [ PuncturedCode, [ obj.cons, [1] ]];
fi;
return DoTheTrick( obj, 2, InfoLine(n, k, obj.d,
"by puncturing of:", spaces, prefix) );
elif i = 3 then # Extending
obj := RecurseBound(n-1, k, spaces, "");
if q = 2 and IsOddInt(obj.d) then
obj.d := obj.d + 1;
fi;
if IsBound(obj.lastman) and obj.lastman = 3 then
obj.cons[2][2] := obj.cons[2][2] + 1;
else
obj.cons := [ ExtendedCode, [ obj.cons, 1 ]];
fi;
return DoTheTrick( obj, 3, InfoLine(n, k, obj.d,
"by extending:", spaces, prefix) );
# begin CJ 25 April 2006
elif i = 20 then # Taking subcode
obj := RecurseBound(n, k+1, spaces, "");
obj.cons := [ SubCode, [ obj.cons ]];
return DoTheTrick( obj, 20, InfoLine(n, k, obj.d,
"by taking subcode of:", spaces, prefix) );
# end CJ
# Methods for upper bounds:
elif i = 11 then # Shortening
obj := RecurseBound(n-1, k-1, spaces, "");
return DoTheTrick( obj, 11, InfoLine(n, k, obj.d,
# "otherwise shortening would contradict:",
"by considering shortening to:",
spaces, prefix) );
elif i = 12 then # Puncturing
obj := RecurseBound(n-1, k, spaces, "");
obj.d := obj.d + 1;
return DoTheTrick( obj, 12, InfoLine(n, k, obj.d,
# "otherwise puncturing would contradict:",
"by considering puncturing to:",
spaces, prefix) );
elif i = 13 then #Extending
obj := RecurseBound(n+1, k, spaces, "");
if q=2 and IsOddInt(obj.d) then
obj.d := obj.d - 1;
fi;
return DoTheTrick( obj, 13, InfoLine(n, k, obj.d,
"otherwise extending would contradict:",
spaces, prefix) );
else
Error("invalid table entry; table is corrupted");
fi;
else
i := GUAVA_BOUNDS_TABLE[kind][q][n][k];
if i[1] = 0 then # Code from library
if IsBound( GUAVA_REF_LIST.(i[3]) ) then
res.references.(i[3]) := GUAVA_REF_LIST.(i[3]);
else
res.references.(i[3]) := GUAVA_REF_LIST.ask;
fi;
obj := rec( d := i[2], expl := [InfoLine(n, k, i[2],
Concatenation("reference: ", i[3]),
spaces, prefix)], cons := false );
if kind = 1 and not GLOBAL_ALERT then
GUAVA_TEMP_VAR := [n, k];
ReadPackage( "guava",
Concatenation( "tbl/codes", String(q), ".g" ) );
if GUAVA_TEMP_VAR = false then
GLOBAL_ALERT := true;
fi;
obj.cons := GUAVA_TEMP_VAR;
fi;
return obj;
elif i[1] = 4 then # Construction B
obj := RecurseBound(n+i[2],k+i[2]-1, spaces, "");
obj.cons := [ConstructionBCode, [obj.cons]];
# Add(obj.expl, InfoLine(n, k, obj.d, Concatenation(
# "by construction B (deleting ",String(i[2]),
# " coordinates of a word in the dual)"),
# spaces, prefix) );
Add(obj.expl, InfoLine(n, k, obj.d, Concatenation(
"by applying construction B to a [",
String(n+i[2]), ",", String(k+i[2]-1), ",",
String(obj.d), "] code"), spaces, prefix) );
Unbind(obj.lastman);
return obj;
elif i[1] = 5 then # u | u+v construction
obj := RecurseBound(n/2, i[2], spaces + 4, "C1: ");
obj2 :=RecurseBound(n/2, k-i[2], spaces + 4, "C2: ");
d1 := obj.d;
obj.cons := [UUVCode,[obj.cons, obj2.cons]];
obj.d := Minimum( 2 * obj.d, obj2.d );
obj.expl := Concatenation(obj2.expl, obj.expl);
Add(obj.expl, InfoLine(n, k, obj.d,
Concatenation("by the u|u+v construction applied to C1 [",
String(n/2), ",", String(i[2]), ",",
String(d1), "] and C2 [", String(n/2),
",", String(k-i[2]), ",", String(obj2.d), "]: "),
spaces, prefix) );
# "u|u+v construction of C1 and C2:", spaces, prefix));
Unbind(obj.lastman);
return obj;
elif i[1] = 22 and q > 2 then # u | u+av | u+v+w construction, for GF(q) where q > 2
obj := RecurseBound(n/3, i[2], spaces + 4, "C1: "); d1 := obj.d;
obj2 :=RecurseBound(n/3, i[3], spaces + 4, "C2: "); d2 := obj2.d;
obj3 :=RecurseBound(n/3, k-i[2]-i[3], spaces + 4, "C2: "); d3 := obj3.d;
obj.cons := false; # [UUAVUVWCode,[obj.cons, obj2.cons, obj3.cons]];
obj.d := n;
if (i[2] > 0) then obj.d := Minimum( obj.d, 3*d1 ); fi;
if (i[3] > 0) then obj.d := Minimum( obj.d, 2*d2 ); fi;
if (k-(i[2]+i[3]) > 0) then obj.d := Minimum( obj.d, d3 ); fi;
obj.expl := Concatenation(obj3.expl, obj2.expl, obj.expl);
Add(obj.expl, InfoLine(n, k, obj.d,
Concatenation("by the u|u+av|u+v+w construction applied to C1 [",
String(n/3), ",", String(i[2]), ",",
String(d1), "] and C2 [", String(n/3),
",", String(i[3]), ",", String(d2), "] and C3 [",
String(n/3), ",", String(k-i[2]-i[3]), ",",
String(d3), "]: "), spaces, prefix) );
Unbind(obj.lastman);
return obj;
elif i[1] = 6 then # Concatenation
obj := RecurseBound(n-i[2], k, spaces + 4, "C1: ");
obj2 := RecurseBound(i[2], k, spaces + 4, "C2: ");
d1 := obj.d;
obj.cons := [ConcatenationCode,[obj.cons, obj2.cons]];
obj.d := obj.d + obj2.d;
obj.expl := Concatenation(obj2.expl, obj.expl);
Add(obj.expl, InfoLine(n, k, obj.d,
Concatenation("by concatenation of C1 [",
String(n-i[2]), ",", String(k), ",",
String(d1), "] and C2 [", String(i[2]), ",",
String(k), ",", String(obj2.d), "]: "),
spaces, prefix) );
# "concatenation of C1 and C2:", spaces, prefix));
Unbind(obj.lastman);
return obj;
elif i[1] = 7 then # ResidueCode
# begin CJ 27 April 2006
# The current Brouwer's table contains some 'MYSTERY' codes, these codes are
# resulted from Construction A.
if ((q = 2 and i[2] > 257) or (q = 3 and i[2] > 243) or (q = 4 and i[2] > 256)) then
d1 := QuoInt((i[2]-n), q) + SignInt((i[2]-n) mod q);
obj := rec( d := d1, expl := [InfoLine(n, k, d1,
Concatenation("by construction A (taking residue) of a [",
String(i[2]), ",", String(k+1), ",", String(i[2]-n), "]",
" MYSTERY code, contact A.E. Brouwer (aeb@cwi.nl)"),
spaces, prefix)], cons := false );
Unbind(obj.lastman);
return obj;
fi;
# end CJ
obj := RecurseBound(i[2], k+1, spaces, "");
obj.d := QuoInt(obj.d, q) + SignInt(obj.d mod q);
Add(obj.expl, InfoLine(n, k, obj.d, "by construction A (taking residue) of:",
spaces, prefix) );
obj.cons := [ResidueCode, [obj.cons]];
Unbind(obj.lastman);
return obj;
elif i[1] = 14 then # Construction B
obj := RecurseBound(n-i[2], k-i[2]+1, spaces, "");
Add(obj.expl, InfoLine(n, k, obj.d,
# "otherwise construction B would contradict:", spaces,
"by construction B applied to:", spaces,
prefix) );
Unbind(obj.lastman);
return obj;
# begin CJ, 25 April 2006
elif i[1] = 15 then # the Griesmer bound (non recursive)
obj := rec( d:=i[2], expl := [InfoLine(n, k, i[2],
"by the Griesmer bound", spaces, prefix)], cons:=false );
Unbind(obj.lastman);
return obj;
elif i[1] = 16 then # one-step Griesmer bound
obj := RecurseBound(n-(i[2]+1), k-1, spaces, "");
obj.d := i[2];
Add(obj.expl, InfoLine(n, k, obj.d,
"by a one-step Griesmer bound from:", spaces, prefix) );
Unbind(obj.lastman);
return obj;
elif i[1] = 21 then # Construction B2
obj := RecurseBound(n+i[2], k+i[2]-(2*i[3])-1, spaces, "");
obj.cons := [ConstructionB2Code, [obj.cons]];
obj.d := obj.d - (2*i[3]);
Add(obj.expl, InfoLine(n, k, obj.d, Concatenation(
"by applying construction B2 to a [", String(n+i[2]), ",",
String(k+i[2]-(2*i[3])-1), ",", String(obj.d+(2*i[3])),
"] code"), spaces, prefix) );
Unbind(obj.lastman);
return obj;
#end CJ
else
Error("invalid table entry; table is corrupted");
fi;
fi;
end;
#F Function body
if Length(arg) < 2 or Length(arg) > 4 then
Error("usage: OptimalLinearCode( <n>, <k> [, <F>] )");
fi;
n := arg[1];
k := arg[2];
q := 2;
if Length(arg) > 2 then
if IsInt(arg[3]) then
q := arg[3];
else
q := Size(arg[3]);
fi;
fi;
if k > n then
Error("k must be less than or equal to n");
fi;
# Check that right tables are present
if not IsBound(GUAVA_REF_LIST) or Length(RecNames(GUAVA_REF_LIST))=0 then
ReadPackage( "guava", "tbl/refs.g" );
fi;
res := rec(n := n,
k := k,
q := q,
references := rec(),
construction := false);
if not ( IsBound(GUAVA_BOUNDS_TABLE[1][q]) and
IsBound(GUAVA_BOUNDS_TABLE[2][q]) ) and
q > 4 then
res.lowerBound := 1;
res.upperBound := n - k + 1;
return res;
# Error("boundstable for q = ", q, " is not implemented.");
else
ReadPackage( "guava", Concatenation( "tbl/bdtable", String(q), ".g" ) );
fi;
if n > Length(GUAVA_BOUNDS_TABLE[1][q]) then
# no error should be returned here, otherwise Upper and
# LowerBoundMinimumDistance would not work. The upper bound
# could easily be sharpened by the Griesmer bound and
# if n - k > Sz then
# upperbound >= n - k + 1;
# else
# upperbound <= Ub[ Sz ][ k - n + Sz ]
# fi;
# lowerbound >= Lb[ Sz ][Minimum(Sz, k)]
res.lowerBound := 1;
res.upperBound := n - k + 1;
return res;
# Error("no data for n > ", Length(GUAVA_BOUNDS_TABLE[1][q]));
fi;
if Length(arg) < 4 or arg[4] then
kind := 1;
GLOBAL_ALERT := (Length(arg) = 4);
obj := RecurseBound( n, k, 0, "");
if not GLOBAL_ALERT then
res.construction := obj.cons;
fi;
res.lowerBound := obj.d;
res.lowerBoundExplanation := Reversed( obj.expl );
fi;
if Length(arg) < 4 or not arg[4] then
kind := 2;
obj := RecurseBound( n, k, 0, "");
res.upperBound := obj.d;
res.upperBoundExplanation := Reversed( obj.expl );
fi;
return res;
end);
#############################################################################
##
#F StringFromBoundsInfo . . . . . . . functions for bounds record
## PrintBoundsInfo . . . . . . . . .
## DisplayBoundsInfo . . . . . . . .
##
## These functions are not automatically called. The user must
## specifically call them if desired. They are intended for use
## with the Bounds Info record returned by the BoundsMinimumDistance
## function only. They replace the BoundsOps functions of the GAP3
## version of GUAVA and provide a way to neatly print and display
## the information returned by BoundsMinimumDistance.
## Ex: PrintBoundsInfo(BoundsMinimumDistance(13,5,3));
##
StringFromBoundsInfo := function(R)
local line;
line := Concatenation("an optimal linear [", String(R.n), ",",
String(R.k), ",d] code over GF(", String(R.q), ") has d");
if R.upperBound <> R.lowerBound then
Append(line,Concatenation(" in [", String(R.lowerBound),"..",
String(R.upperBound),"]"));
else
Append(line,Concatenation("=",String(R.lowerBound)));
fi;
return line;
end;
PrintBoundsInfo := function(R)
Print(StringFromBoundsInfo(R), "\n");
end;
DisplayBoundsInfo := function(R)
local i, ref;
PrintBoundsInfo(R);
if IsBound(R.lowerBoundExplanation) then
for i in [1..SizeScreen()[1]-2] do Print( "-" ); od; Print( "\n" );
for i in R.lowerBoundExplanation do
Print(i, "\n");
od;
fi;
if IsBound(R.upperBoundExplanation) then
for i in [1..SizeScreen()[1]-2] do Print( "-" ); od; Print( "\n" );
for i in R.upperBoundExplanation do
Print(i, "\n");
od;
fi;
if IsBound(R.references) and Length(RecNames(R.references)) > 0 then
for i in [1..SizeScreen()[1]-2] do Print( "-" ); od; Print( "\n" );
for i in RecNames(R.references) do
Print("Reference ", i, ":\n");
for ref in R.references.(i) do
Print(ref, "\n");
od;
od;
fi;
end;
[ Verzeichnis aufwärts0.103unsichere Verbindung
]
|
2026-03-28
|