コード例 #1
0
ファイル: glue.py プロジェクト: punkdit/qupy
def test_glue():

    m = argv.get("m", 9)
    n = argv.get("n", 10)

    d = argv.get("d", 0)
    p = argv.get("p", 0.5)
    weight = argv.weight

    H1 = rand2(m, n, p, weight)
    G1 = find_kernel(H1)
    G1t = G1.transpose()
    H1t = H1.transpose()
    A1 = Chain([G1, H1t])
    k1 = len(G1)

    print("H1")
    print(fstr(H1))
    print()
    print(fstr(G1))

    w = wenum(H1)
    print("wenum:", [len(wi) for wi in w])

    H2 = rand2(m, n, p, weight)
    H2t = H2.transpose()
    G2 = find_kernel(H2)
    G2t = G2.transpose()
    A2 = Chain([G2, H2t])
    k2 = len(G2)

    print("H2")
    print(fstr(H2))
    print()
    print(fstr(G2))

    w = wenum(H2)
    print("wenum:", [len(wi) for wi in w])

    if k1 != k2:
        return
    k = k1

    I = identity2(k)
    B = Chain([I, zeros2(k, 0)])

    a = zeros2(n, k)
    for i in range(k):
        a[i, i] = 1
    f1 = Morphism(B, A1, [dot2(G1, a), a, zeros2(m, 0)])
    f2 = Morphism(B, A2, [dot2(G2, a), a, zeros2(m, 0)])

    a, b, C, _ = chain.pushout(f1, f2)

    H = C[1].transpose()
    print("H:")
    print(fstr(H))

    w = wenum(H)
    print("wenum:", [len(wi) for wi in w])
コード例 #2
0
    def is_stab(self, v):
        write('/')
        Hx_t = self.Hx.transpose()

#        # Hx_t u = v
#        # u = Hx_t^-1 v
#        if self.Hx_t_inv is None:
#            Hx_t_inv = solve.pseudo_inverse(Hx_t)
#            self.Hx_t_inv = Hx_t_inv
#        Hx_t_inv = self.Hx_t_inv
#        u = dot2(Hx_t_inv, v)

        u = dot2(self.Tz, v)

        #u = solve.solve(Hx_t, v)
        #if u is not None:
        if eq2(dot2(Hx_t, u), v):
            #print "[%s]"%u.sum(),
            v1 = dot2(Hx_t, u)
            assert ((v+v1)%2).max() == 0
#            assert self.is_stab_0(v) # double check
        else:
#            assert not self.is_stab_0(v) # double check
            u = None
        write('\\')
        return u is not None
コード例 #3
0
ファイル: glue.py プロジェクト: punkdit/qupy
def glue_pairs(H1, H2, pairs):

    m1, n1 = H1.shape
    m2, n2 = H2.shape
    k = len(pairs)

    A1 = Chain([H1])
    A2 = Chain([H2])
    C = Chain([identity2(k)])

    C1n = zeros2(n1, k)
    for idx, pair in enumerate(pairs):
        i, j = pair
        C1n[i, idx] = 1
    C1m = dot2(H1, C1n)
    C1 = Morphism(C, A1, [C1m, C1n])

    C2n = zeros2(n2, k)
    for idx, pair in enumerate(pairs):
        i, j = pair
        C2n[j, idx] = 1
    C2m = dot2(H2, C2n)
    C2 = Morphism(C, A2, [C2m, C2n])

    AD, BD, D, _ = chain.pushout(C1, C2)

    H = D[0]
    #print(H.shape)
    #print(H)
    return H
コード例 #4
0
ファイル: glue.py プロジェクト: punkdit/qupy
def glue_quantum(Hx1, Hz1, Hx2, Hz2, pairs):

    mx1, n1 = Hx1.shape
    mx2, n2 = Hx2.shape
    mz1, _ = Hz1.shape
    mz2, _ = Hz2.shape
    k = len(pairs)

    A1 = Chain([Hz1, Hx1.transpose()])
    A2 = Chain([Hz2, Hx2.transpose()])
    C = Chain([identity2(k), zeros2(k, 0)])

    C1n = zeros2(n1, k)
    for idx, pair in enumerate(pairs):
        i, j = pair
        C1n[i, idx] = 1
    C1m = dot2(Hz1, C1n)
    C1 = Morphism(C, A1, [C1m, C1n, zeros2(mx1, 0)])

    C2n = zeros2(n2, k)
    for idx, pair in enumerate(pairs):
        i, j = pair
        C2n[j, idx] = 1
    C2m = dot2(Hz2, C2n)
    C2 = Morphism(C, A2, [C2m, C2n, zeros2(mx2, 0)])

    AD, BD, D, _ = chain.pushout(C1, C2)

    Hz, Hxt = D[0], D[1]
    #print(H.shape)
    #print(H)

    return Hz, Hxt.transpose()
コード例 #5
0
    def glue(self, i1, i2):
        assert i1!=i2

        Hx = self.Hx
        Hz = self.Hz
        mx, n = Hx.shape
        mz, _ = Hz.shape
        k = 1 
    
        A = Chain([Hz, Hx.transpose()])
        C  = Chain([identity2(k), zeros2(k, 0)])
    
        fn = zeros2(n, 1)
        fn[i1, 0] = 1 
        fm = dot2(Hz, fn) 
        f = Morphism(C, A, [fm, fn, zeros2(mx, 0)])
    
        gn = zeros2(n, 1)
        gn[i2, 0] = 1 
        gm = dot2(Hz, gn) 
        g = Morphism(C, A, [gm, gn, zeros2(mx, 0)])
    
        _, _, D = equalizer(f, g)
    
        Hz, Hxt = D[0], D[1]
        Hx = Hxt.transpose()
        code = CSSCode(Hx=Hx, Hz=Hz)
        return code
コード例 #6
0
def lookup_distance(code):
    n = code.n
    Hz, Tx = code.Hz, code.Tx

    d = n
    u = zeros2(n)
    for i0 in range(n):
        u[i0] = 1
        if dot2(Hz, u).sum() == 0:
            #print("*", shortstr(u))
            d = min(d, 1)
        for i1 in range(i0+1, n):
            u[i1] = 1
            if dot2(Hz, u).sum() == 0:
                #print("*", shortstr(u))
                if d>2:
                    print("d=", d)
                d = min(d, 2)
            for i2 in range(i1+1, n):
                u[i2] = 1
                if dot2(Hz, u).sum() == 0:
                    #print("*", shortstr(u))
                    if d>3:
                        print("d=", d)
                    d = min(d, 3)
                for i3 in range(i2+1, n):
                    u[i3] = 1
                    if dot2(Hz, u).sum() == 0:
                        #print("*", shortstr(u))
                        d = min(d, 4)
                    u[i3] = 0
                u[i2] = 0
            u[i1] = 0
        u[i0] = 0
    return d
コード例 #7
0
ファイル: glue.py プロジェクト: punkdit/qupy
def glue_self(Hx, Hz, pairs):
    mx, n = Hx.shape
    mz, _ = Hz.shape
    k = len(pairs)

    A = Chain([Hz, Hx.transpose()])
    C = Chain([identity2(k), zeros2(k, 0)])

    fn = zeros2(n, k)
    for idx, pair in enumerate(pairs):
        i1, i2 = pair
        fn[i1, idx] = 1
    fm = dot2(Hz, fn)
    f = Morphism(C, A, [fm, fn, zeros2(mx, 0)])

    gn = zeros2(n, k)
    for idx, pair in enumerate(pairs):
        i1, i2 = pair
        gn[i2, idx] = 1
    gm = dot2(Hz, gn)
    g = Morphism(C, A, [gm, gn, zeros2(mx, 0)])

    _, _, D = chain.equalizer(f, g)

    Hz, Hxt = D[0], D[1]
    return Hxt.transpose(), Hz
コード例 #8
0
ファイル: glue.py プロジェクト: punkdit/qupy
def make_q(n, m, weight=None):
    k = n - 2 * m
    assert k >= 0

    assert m > 0
    Hx = [rand2(1, n, weight=weight)[0]]
    Hz = []
    while 1:
        _Hx = array2(Hx)
        while 1:
            v = rand2(1, n, weight=weight)
            if dot2(Hx, v.transpose()).sum() == 0:
                break
        Hz.append(v[0])
        if len(Hz) == m:
            break
        while 1:
            v = rand2(1, n, weight=weight)
            if dot2(Hz, v.transpose()).sum() == 0:
                break
        Hx.append(v[0])
    Hx = array2(Hx)
    Hz = array2(Hz)
    assert dot2(Hx, Hz.transpose()).sum() == 0

    return Hx, Hz
コード例 #9
0
ファイル: glue.py プロジェクト: punkdit/qupy
def score(code, p=0.05, N=10000):
    # each bit gets a score: higher is worse
    decoder = RadfordBPDecoder(2, code.Hz)
    n = code.n
    counts = numpy.zeros(n, dtype=int)

    err = 0
    for trial in range(N):
        err_op = ra.binomial(1, p, (code.n, ))
        err_op = err_op.astype(numpy.int32)
        #write(str(err_op.sum()))
        s = dot2(code.Hz, err_op)  # syndrome
        #write(":s%d:"%s.sum())
        op = decoder.decode(p, err_op, verbose=False)
        success = False
        if op is not None:
            op = (op + err_op) % 2
            # Should be a codeword of Hz (kernel of Hz)
            assert dot2(code.Hz, op).sum() == 0
            #write("%d:"%op.sum())
            if dot2(code.Lz, op).sum():
                #                counts += op
                counts += err_op
            else:
                success = True
        if not success:
            err += 1

    return counts, (err / N)
コード例 #10
0
ファイル: glue.py プロジェクト: punkdit/qupy
def glue2(H1, H2, i1, i2):

    m1, n1 = H1.shape
    m2, n2 = H2.shape

    A1 = Chain([H1])
    A2 = Chain([H2])
    C = Chain([array2([[1]])])

    C1n = zeros2(n1, 1)
    C1n[i1, 0] = 1
    C1m = dot2(H1, C1n)
    C1 = Morphism(C, A1, [C1m, C1n])

    C2n = zeros2(n2, 1)
    C2n[i2, 0] = 1
    C2m = dot2(H2, C2n)
    C2 = Morphism(C, A2, [C2m, C2n])

    AD, BD, D, _ = chain.pushout(C1, C2)

    H = D[0]
    #print(H.shape)
    #print(H)
    return H
コード例 #11
0
ファイル: glue.py プロジェクト: punkdit/qupy
def glue_self_classical(Hz, pairs):
    mz, n = Hz.shape
    k = len(pairs)

    A = Chain([Hz])
    C = Chain([identity2(k)])

    fn = zeros2(n, k)
    for idx, pair in enumerate(pairs):
        i1, i2 = pair
        fn[i1, idx] = 1
    fm = dot2(Hz, fn)
    f = Morphism(C, A, [fm, fn])

    gn = zeros2(n, k)
    for idx, pair in enumerate(pairs):
        i1, i2 = pair
        gn[i2, idx] = 1
    gm = dot2(Hz, gn)
    g = Morphism(C, A, [gm, gn])

    _, _, D = chain.equalizer(f, g)

    Hz = D[0]
    return Hz
コード例 #12
0
 def eq(self, other):
     "Two codes are equal if their generating matrices have the same span."
     G1, G2 = self.G, other.G
     if len(G1) != len(G2):
         return False
     A = dot2(self.H, other.G.transpose())
     B = dot2(other.H, self.G.transpose())
     assert (A.sum() == 0) == (B.sum() == 0)
     return A.sum() == 0
コード例 #13
0
ファイル: asymplectic.py プロジェクト: punkdit/qupy
 def check(self):
     # check symplectic condition
     A = self.A
     nn = self.n
     n = (nn - 1) // 2
     B = A[:2 * n, :2 * n]
     F = symplectic_form(n)
     lhs = dot2(dot2(B.transpose(), F), B)
     return numpy.alltrue(lhs == F)
コード例 #14
0
def pushout(a, b, _amorph=None, _bmorph=None, _chain=None, check=True):
    """
        Construct pushout of Morphism's a, b.
        If supplied with another cocone over a, b then
        also construct unique Morphism to that cocone.
    """
    assert isinstance(a, Morphism)
    assert isinstance(b, Morphism)
    assert a.src == b.src

    src = a.src
    n = len(src)
    amorph = []
    bmorph = []
    chain = []
    aprev = None
    bprev = None
    for i in range(n + 1):
        a1, b1, c1 = solve.pushout(a[i], b[i], aprev, bprev)
        amorph.append(a1)
        bmorph.append(b1)
        chain.append(c1)
        aprev = compose2(a.tgt[i], a1)
        bprev = compose2(b.tgt[i], b1)
        #_a1, _b1, _ = solve.pushout(a[i], b[i])
        #assert eq2(a1, _a1)
        #assert eq2(b1, _b1)
    chain = Chain(chain[1:])
    amorph = Morphism(a.tgt, chain, amorph)
    bmorph = Morphism(b.tgt, chain, bmorph)
    if check:
        assert amorph * a == bmorph * b
    assert (_amorph is None) == (_bmorph is None) == (_chain is None)
    morph = None
    if _amorph is not None:
        assert amorph.tgt == bmorph.tgt
        assert _amorph * a == _bmorph * b, "not a cocone!"
        Ds = []
        for i in range(n + 1):
            a1, b1, d = solve.pushout(a[i], b[i], _amorph[i], _bmorph[i])
            Ds.append(d)
            assert eq2(dot2(d, a1), _amorph[i])
            assert eq2(dot2(d, b1), _bmorph[i])
            assert eq2(a1, amorph[i])
            assert eq2(b1, bmorph[i])
        morph = Morphism(chain, _chain, Ds)
        if check:
            #lhs = morph * amorph
            #rhs = _amorph
            #print(lhs.shape)
            #print(rhs.shape)
            assert morph * amorph == _amorph
            assert morph * bmorph == _bmorph

    return amorph, bmorph, chain, morph
コード例 #15
0
def build(items):
    items = items.strip().split()
    #print(items)
    rows = []
    n = None
    for item in items:
        assert n is None or len(items)==n
        n = len(items)
        row = []
        for i in item:
            if i=="X":
                row += [1, 0]
            elif i=="Z":
                row += [0, 1]
            elif i=="Y":
                row += [1, 1]
            elif i=="I":
                row += [0, 0]
            else:
                assert 0
        rows.append(row)
    H = solve.array2(rows)
    #print(H)
    J = sy_form(n)
    HJ = solve.dot2(H, J)
    #print(HJ)
    T = solve.pseudo_inverse(HJ.transpose())
    #print(T)
    TJ = solve.dot2(T, J)
    #print(TJ)
    #print(solve.dot2(TJ, H.transpose())) # identity

    ops = []
    for row in T:
        op = []
        for i in range(n):
            opi = list(row[2*i : 2*(i+1)])
            if opi == [0, 0]:
                op.append(I)
                #write("I")
            elif opi == [1, 0]:
                op.append(X)
                #write("X")
            elif opi == [0, 1]:
                op.append(Z)
                #write("Z")
            elif opi == [1, 1]:
                op.append(Y)
                #write("Y")
            else:
                assert 0, opi
        op = reduce(matmul, op)
        ops.append(op)
        #write("\n")
    return ops
コード例 #16
0
def sparsecss(n, mx, mz, weight=8, **kw):

    print("sparsecss", n, mx, mz)
    k = n-mx-mz
    assert k>=0

    vec = lambda n=n, weight=weight : rand2(1, n, weight=weight)

    Hz = zeros2(0, n)
    Hx = zeros2(0, n)

    Hx = append2(Hx, vec())

    while len(Hz)<mz or len(Hx)<mx:

        # append2 Hz
        rows = shortstr(Hz).split()
        #print rows
        while Hz.shape[0]<mz:
            v = vec()
            u = dot2(Hx, v.transpose())
            if u.sum() == 0 and shortstr(v) not in rows:
                Hz = append2(Hz, v)
                break
            
        # append2 Hx
        rows = shortstr(Hx).split()
        #print rows
        while Hx.shape[0]<mx:
            v = vec()
            u = dot2(Hz, v.transpose())
            if u.sum() == 0 and shortstr(v) not in rows:
                Hx = append2(Hx, v)
                break

        print(shortstrx(Hz, Hx))
        print()

    bits = []
    for i in range(n):
        if Hx[:, i].sum() == 0:
            bits.append(i)
        elif Hz[:, i].sum() == 0:
            bits.append(i)

    for i in reversed(bits):
        Hx = numpy.concatenate(
            (Hx[:, :i], Hx[:, i+1:]), axis=1)
        Hz = numpy.concatenate(
            (Hz[:, :i], Hz[:, i+1:]), axis=1)

    #print shortstrx(Hx, Hz)

    C = CSSCode(Hx=Hx, Hz=Hz, **kw)
    return C
コード例 #17
0
ファイル: glue.py プロジェクト: punkdit/qupy
def glue_gcolor():
    from qupy.ldpc.gcolor import Lattice
    l = argv.get('l', 1)
    lattice = Lattice(l)
    #code = lattice.build_code()
    H = lattice.Hx
    print("H:", H.shape)
    print(shortstr(H))
    m, n = H.shape
    H1 = zeros2(m + 1, n + 1)
    H1[1:, 1:] = H
    H1[0, :] = 1
    #    print()
    #    print(shortstr(H1))
    #    for genus in range(1, 5):
    #        print(genus, strong_morthogonal(H1, genus))

    H = H1

    genus = argv.get("genus", 3)

    H = H.astype(numpy.int32)
    n = H.shape[1]

    if argv.scramble:
        R = rand2(m, m)
        H = dot2(R, H)

    print("H:", H.shape)
    print(shortstrx(H))
    assert dot2(H, H.transpose()).sum() == 0

    i0 = argv.get("i0", 0)
    i1 = argv.get("i1", i0)
    i2 = argv.get("i2", n)
    i3 = argv.get("i3", i2 + 1)
    # glue i0<-->i2 and i1<-->i3

    H2 = direct_sum(H, H)
    print(H2.shape)
    print(shortstrx(H2))
    assert strong_morthogonal(H2, genus)
    print()

    H3 = glue_self_classical(H2, [(i0, i2), (i1, i3)])
    print(H3.shape)
    print(shortstrx(H3))
    assert strong_morthogonal(H3, genus)

    print()
    print(shortstr((H2[:m, 1:n] + H3[:m, 1:n]) % 2))
    #print(eq2(H2[m+2:, i1+2:], H3[m:, i1:]))

    #print(classical_distance(H3))
    return H3
コード例 #18
0
def x_split(C0, build=True, **kw):
    "split the x-stabilizers of C0"

    #print "x_split"

    mz, n, mx = C0.mz, C0.n+C0.mx, 2*C0.mx

    #print C0.longstr()

    Hz = zeros2(mz, n)
    Hz[:, :C0.n] = C0.Hz

    Hx = zeros2(mx, n)

    #print "Hz:"
    #print shortstrx(Hz)

    for i in range(C0.mx):

        op = C0.Hx[i]
        #Hx[:C0.mx-1, :C0.n] = pop2(C0.Hx, i)
    
        #print "Hx:"
        #print shortstrx(Hx)
    
        idxs = [j for j in range(C0.n) if op[j]]
    
        idxs0 = idxs[:len(idxs)//2]
        idxs1 = idxs[len(idxs)//2:]
        
        #print idxs, idxs0, idxs1
    
        i0, i1 = 2*i, 2*i+1
        for j in idxs0:
            Hx[i0, j] = 1
        for j in idxs1:
            Hx[i1, j] = 1
        Hx[i0, C0.n+i] = 1
        Hx[i1, C0.n+i] = 1

        #print "Hx:"
        #print shortstrx(Hx)
    
        for j in range(mz):
            if dot2(Hz[j], Hx[i0]):
                assert dot2(Hz[j], Hx[i1]) # brilliant!
                Hz[j, C0.n+i] = 1

    C1 = CSSCode(Hx=Hx, Hz=Hz, build=build, **kw)

    #print C1.weightsummary()

    return C1
コード例 #19
0
ファイル: asymplectic.py プロジェクト: punkdit/qupy
 def inverse(self):
     A = self.A
     nn = self.n
     n = (nn - 1) // 2
     B = A[:2 * n, :2 * n]  # symplectic
     v = A[:2 * n, 2 * n]  # translation, shape (2*n,)
     F = symplectic_form(n)
     Fi = F  # an involution
     Bi = dot2(Fi, dot2(B.transpose()), F)
     A1 = A.copy()
     A1[:2 * n, :2 * n] = Bi
     A1[:2 * n, 2 * n] = dot2(-Bi, v)
     return Clifford(A1)
コード例 #20
0
 def __mul__(self, other):
     "composition: apply other then self"
     assert isinstance(other, Morphism)
     assert other.tgt == self.src
     n = len(self)
     Ds = [dot2(self[i], other[i]) for i in range(n)]
     return Morphism(other.src, self.tgt, Ds)
コード例 #21
0
ファイル: gcolor.py プロジェクト: punkdit/qupy
 def get_syndrome(self, op):
     syndrome = []
     for i in range(len(self.Gz)):
         r = dot2(op, self.Gz[i].transpose())
         if r:
             syndrome.append(i)
     return syndrome
コード例 #22
0
ファイル: symplectic.py プロジェクト: punkdit/qupy
def test_isotropic():

    n = 3
    gen, _ = get_gen(n)
    assert len(mulclose_fast(gen)) == 1451520
    return

    n = argv.get("n", 3)
    F = Matrix.symplectic_form(n).A

    found = []
    for A in all_codes(n, 2 * n):
        B = dot2(dot2(A, F), A.transpose())
        if B.sum() == 0:
            A = Matrix(A)
            found.append(A)
            #print(A)

    found = set(found)
    print(len(found))

    gen, _ = get_gen(n)
    #gen = get_transvect(n)

    orbit = set()
    A = iter(found).__next__()

    bdy = [A]
    orbit = set(bdy)
    while bdy:
        _bdy = []
        for A in bdy:
            print(A)
            for g in gen:
                B = A * g
                print(B)
                print()
                B = B.normal_form()
                print(B)
                print()
                assert B in found
                if B not in orbit:
                    _bdy.append(B)
                    orbit.add(B)
        bdy = _bdy

    print(len(orbit))