mirror of
https://github.com/qwjyh/QuantumLegos.jl.git
synced 2025-06-29 16:19:19 +09:00
init (migrating and renaming)
This commit is contained in:
commit
f772e27182
19 changed files with 2262 additions and 0 deletions
6
docs/Project.toml
Normal file
6
docs/Project.toml
Normal file
|
@ -0,0 +1,6 @@
|
|||
[deps]
|
||||
DataStructures = "864edb3b-99cc-5e75-8d2d-829cb0a9cfe8"
|
||||
Documenter = "e30172f5-a6a5-5a46-863b-614d45cd2de4"
|
||||
IterTools = "c8e1da08-722c-5040-9ed9-7db0dc04731e"
|
||||
Legos = "6c892f99-6e80-4382-8dc3-97545b5cb80e"
|
||||
StaticArrays = "90137ffa-7385-5640-81b9-e52037218182"
|
23
docs/make.jl
Normal file
23
docs/make.jl
Normal file
|
@ -0,0 +1,23 @@
|
|||
#! format: off
|
||||
using Legos
|
||||
using Documenter
|
||||
|
||||
DocMeta.setdocmeta!(Legos, :DocTestSetup, :(using Legos); recursive=true)
|
||||
|
||||
makedocs(;
|
||||
modules=[Legos],
|
||||
authors="",
|
||||
# repo="",
|
||||
sitename="Legos.jl",
|
||||
format=Documenter.HTML(;
|
||||
prettyurls=get(ENV, "CI", "false") == "true",
|
||||
edit_link="main",
|
||||
assets=String[],
|
||||
),
|
||||
pages=[
|
||||
"Home" => "index.md",
|
||||
"PauliOps" => "pauliops.md",
|
||||
"checkmatrix.md",
|
||||
"distance.md",
|
||||
],
|
||||
)
|
82
docs/src/checkmatrix.md
Normal file
82
docs/src/checkmatrix.md
Normal file
|
@ -0,0 +1,82 @@
|
|||
# Details on check matrix operations
|
||||
|
||||
## Basic features of check matrix
|
||||
|
||||
- All action on state can be represented as operations on check matrix.
|
||||
- QuantumLegos which don't connect each other are represented by block diagonal check matrix.
|
||||
|
||||
Thus, one needs only one check matrix to represent state.
|
||||
|
||||
- Generated group from generators represented by check matrix is invariant under row-swap and row-multiplying transforms on the check matrix.
|
||||
|
||||
Thus, one can freely perform these row operations on check matrices.
|
||||
|
||||
## Construction of check matrices and retrieving features
|
||||
|
||||
Use [`CheckMatrix`](@ref) from `Matrix{Bool}` and [`checkmatrix`](@ref) from `Vector{PauliOp}`.
|
||||
|
||||
```@docs
|
||||
CheckMatrix
|
||||
checkmatrix
|
||||
```
|
||||
|
||||
Get xpart and zpart of check matrix.
|
||||
|
||||
```@docs
|
||||
QuantumLegos.xpart
|
||||
QuantumLegos.zpart
|
||||
```
|
||||
|
||||
Get generators from check matrix with [`generators`](@ref).
|
||||
|
||||
```@docs
|
||||
generators
|
||||
```
|
||||
|
||||
See also, [`GeneratedPauliGroup`](@ref) and [`Base.Set`](https://docs.julialang.org/en/v1/base/collections/#Base.Set) to get group generated by generators.
|
||||
|
||||
## Direct sum
|
||||
|
||||
Used when adding lego without edge.
|
||||
|
||||
```@docs
|
||||
QuantumLegos.direct_sum
|
||||
```
|
||||
|
||||
## Self-tracing
|
||||
|
||||
### self-tracing
|
||||
|
||||
```@docs
|
||||
QuantumLegos.self_trace!
|
||||
```
|
||||
|
||||
During self-tracing, pre-formatting and post-formatting described below is performed.
|
||||
|
||||
### pre-formatting
|
||||
|
||||
```@docs
|
||||
QuantumLegos.eliminate_column!
|
||||
```
|
||||
|
||||
```@docs
|
||||
QuantumLegos.align_row!
|
||||
```
|
||||
|
||||
[`QuantumLegos.align_row!`](@ref)
|
||||
|
||||
By this process, all columns to be traced have `1`s on only 1st to 4th rows.
|
||||
So during [`QuantumLegos.self_trace!`](@ref), all stabilizers generated from top three rows are calculated and perform operator matching.
|
||||
|
||||
### post-formatting
|
||||
|
||||
Remove rows which are linear combinations of other rows.
|
||||
|
||||
```@docs
|
||||
QuantumLegos.ref!
|
||||
```
|
||||
|
||||
```@docs
|
||||
QuantumLegos.eliminate_dependent_row!
|
||||
```
|
||||
|
236
docs/src/distance.md
Normal file
236
docs/src/distance.md
Normal file
|
@ -0,0 +1,236 @@
|
|||
# How to calculate code distance from the state.
|
||||
|
||||
!!! warning "WIP"
|
||||
This document is not fully completed.
|
||||
|
||||
## Definition of code distance.
|
||||
|
||||
Let's consider encoding circuit with $1$ logical bit and $k$ physical qubits[^1].
|
||||
Then this encoding has two physical basis, $\ket{0}_L$ and $\ket{1}_L$.
|
||||
The **distance** of this encoding is the minimum bit flip required to convert between $\ket{0}_L$ and $\ket{1}_L$.
|
||||
|
||||
[^1]: Not all state can be formalized like this. TODO
|
||||
|
||||
## Classification of the stabilizers.
|
||||
|
||||
When treating `State`, the logical leg is not assigned and one can treat all stabilizers equally.
|
||||
However, if logical leg is assigned to the state, these stabilizers can be classified to $4$ groups.
|
||||
|
||||
1. stabilizers on physical qubits
|
||||
2. $\bar{X}$, which corresponds to logical $X$
|
||||
3. $\bar{Z}$, which corresponds to logical $Z$
|
||||
4. $\bar{Y}$, which corresponds to logical $Y$
|
||||
|
||||
Let $\ket{V}$ is the dual state of the channel or encoding map $[[n, 1, d]]$,
|
||||
|
||||
```math
|
||||
distance = \min_{S \in stabilizers} \#\left\{ i \mid \bar{Z}_i ≠ S_i \right\}
|
||||
```
|
||||
|
||||
## Calculating code distance from the check matrix.
|
||||
|
||||
TODO: nor required if the performance doesn't matter.
|
||||
|
||||
## Examples
|
||||
|
||||
### $[[5, 1, 3]]$ code
|
||||
|
||||
$[[5, 1, 3]]$ code has $4$ stabilizers generators, $XZZXI, IXZZX, XIXZZ, ZXIXZ$ and $2$ logical operators, $\bar{X} = XXXXX$ and $\bar{Z} = ZZZZZ$.
|
||||
Therefore, stabilizer generators for the corresponding state $[[6, 0]]$ is $IXZZXI, IIXZZX, IXIXZZ, IZXIXZ, XXXXXX, ZZZZZZ$.
|
||||
|
||||
Let's construct $[[6, 0]]$ state on QuantumLegos.jl.
|
||||
```jldoctest 1
|
||||
julia> using QuantumLegos
|
||||
|
||||
julia> stab_513 = pauliop.(["IXZZXI", "IIXZZX", "IXIXZZ", "IZXIXZ", "XXXXXX", "ZZZZZZ"])
|
||||
6-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("IXZZXI")
|
||||
pauliop("IIXZZX")
|
||||
pauliop("IXIXZZ")
|
||||
pauliop("IZXIXZ")
|
||||
pauliop("XXXXXX")
|
||||
pauliop("ZZZZZZ")
|
||||
|
||||
julia> lego_513 = Lego(stab_513)
|
||||
Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IXZZXI"), pauliop("IIXZZX"), pauliop("IXIXZZ"), pauliop("IZXIXZ"), pauliop("XXXXXX"), pauliop("ZZZZZZ")])
|
||||
|
||||
julia> state_513 = State([lego_513], edge.([]))
|
||||
State(Lego[Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IXZZXI"), pauliop("IIXZZX"), pauliop("IXIXZZ"), pauliop("IZXIXZ"), pauliop("XXXXXX"), pauliop("ZZZZZZ")])], Tuple{LegoLeg, LegoLeg}[], CheckMatrix(Bool[0 1 … 0 0; 0 0 … 1 0; … ; 1 1 … 0 0; 0 0 … 1 1], 6, 6))
|
||||
|
||||
```
|
||||
|
||||
Then collect generators of the state.
|
||||
```jldoctest 1
|
||||
julia> normalizers = state_513.cmat |> generators |> GeneratedPauliGroup |> collect
|
||||
64-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("IIIIII")
|
||||
pauliop("IXZZXI")
|
||||
pauliop("IIXZZX")
|
||||
pauliop("IXYIYX")
|
||||
pauliop("IXIXZZ")
|
||||
pauliop("IIZYYZ")
|
||||
pauliop("IXXYIY")
|
||||
pauliop("IIYXXY")
|
||||
pauliop("IZXIXZ")
|
||||
pauliop("IYYZIZ")
|
||||
⋮
|
||||
pauliop("YYIZZI")
|
||||
pauliop("YXZYZX")
|
||||
pauliop("YIIXYX")
|
||||
pauliop("YXYXII")
|
||||
pauliop("YIXYXI")
|
||||
pauliop("YIZZIY")
|
||||
pauliop("YXIIXY")
|
||||
pauliop("YIYIZZ")
|
||||
pauliop("YXXZYZ")
|
||||
|
||||
```
|
||||
|
||||
Get stabilizer and normalizers of the $[[5, 1, 3]]$ code by assigning the first leg as logical.
|
||||
```jldoctest 1
|
||||
julia> stabs = filter(x -> x[1] == PauliOps.I, normalizers)
|
||||
16-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("IIIIII")
|
||||
pauliop("IXZZXI")
|
||||
pauliop("IIXZZX")
|
||||
pauliop("IXYIYX")
|
||||
pauliop("IXIXZZ")
|
||||
pauliop("IIZYYZ")
|
||||
pauliop("IXXYIY")
|
||||
pauliop("IIYXXY")
|
||||
pauliop("IZXIXZ")
|
||||
pauliop("IYYZIZ")
|
||||
pauliop("IZIZYY")
|
||||
pauliop("IYZIZY")
|
||||
pauliop("IYXXYI")
|
||||
pauliop("IZYYZI")
|
||||
pauliop("IYIYXX")
|
||||
pauliop("IZZXIX")
|
||||
|
||||
julia> norm_x = filter(x -> x[1] == PauliOps.X, normalizers)
|
||||
16-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("XXXXXX")
|
||||
pauliop("XIYYIX")
|
||||
pauliop("XXIYYI")
|
||||
pauliop("XIZXZI")
|
||||
pauliop("XIXIYY")
|
||||
pauliop("XXYZZY")
|
||||
pauliop("XIIZXZ")
|
||||
pauliop("XXZIIZ")
|
||||
pauliop("XYIXIY")
|
||||
pauliop("XZZYXY")
|
||||
pauliop("XYXYZZ")
|
||||
pauliop("XZYXYZ")
|
||||
pauliop("XZIIZX")
|
||||
pauliop("XYZZYX")
|
||||
pauliop("XZXZII")
|
||||
pauliop("XYYIXI")
|
||||
|
||||
julia> norm_y = filter(x -> x[1] == PauliOps.Y, normalizers)
|
||||
16-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("YYYYYY")
|
||||
pauliop("YZXXZY")
|
||||
pauliop("YYZXXZ")
|
||||
pauliop("YZIYIZ")
|
||||
pauliop("YZYZXX")
|
||||
pauliop("YYXIIX")
|
||||
pauliop("YZZIYI")
|
||||
pauliop("YYIZZI")
|
||||
pauliop("YXZYZX")
|
||||
pauliop("YIIXYX")
|
||||
pauliop("YXYXII")
|
||||
pauliop("YIXYXI")
|
||||
pauliop("YIZZIY")
|
||||
pauliop("YXIIXY")
|
||||
pauliop("YIYIZZ")
|
||||
pauliop("YXXZYZ")
|
||||
|
||||
julia> norm_z = filter(x -> x[1] == PauliOps.Z, normalizers)
|
||||
16-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("ZZZZZZ")
|
||||
pauliop("ZYIIYZ")
|
||||
pauliop("ZZYIIY")
|
||||
pauliop("ZYXZXY")
|
||||
pauliop("ZYZYII")
|
||||
pauliop("ZZIXXI")
|
||||
pauliop("ZYYXZX")
|
||||
pauliop("ZZXYYX")
|
||||
pauliop("ZIYZYI")
|
||||
pauliop("ZXXIZI")
|
||||
pauliop("ZIZIXX")
|
||||
pauliop("ZXIZIX")
|
||||
pauliop("ZXYYXZ")
|
||||
pauliop("ZIXXIZ")
|
||||
pauliop("ZXZXYY")
|
||||
pauliop("ZIIYZY")
|
||||
|
||||
```
|
||||
|
||||
These normalizers are generated from one logical operator and stabilizers.
|
||||
```jldoctest 1
|
||||
julia> map(x -> x .* pauliop("XXXXXX"), stabs) |> Set == Set(norm_x)
|
||||
true
|
||||
|
||||
julia> map(x -> x .* pauliop("ZZZZZZ"), stabs) |> Set == Set(norm_x)
|
||||
false
|
||||
|
||||
julia> map(x -> x .* pauliop("ZZZZZZ"), stabs) |> Set == Set(norm_z)
|
||||
true
|
||||
|
||||
julia> map(x -> x .* pauliop("YYYYYY"), stabs) |> Set == Set(norm_y)
|
||||
true
|
||||
|
||||
julia> using IterTools
|
||||
|
||||
julia> groupby(x -> x[1], normalizers) .|> Set == Set.([stabs, norm_x, norm_z, norm_y])
|
||||
true
|
||||
|
||||
```
|
||||
|
||||
Define a function to get weight of the operator.
|
||||
```jldoctest 1
|
||||
julia> function weight(x, i = 1)
|
||||
count(x[i:end] .!= PauliOps.I)
|
||||
end
|
||||
weight (generic function with 2 methods)
|
||||
|
||||
julia> weight(pauliop("XIXIXI"))
|
||||
3
|
||||
|
||||
julia> weight(pauliop("XIXIXI"), 2)
|
||||
2
|
||||
|
||||
```
|
||||
|
||||
Calculate coefficients of enumerator polynomial.
|
||||
```jldoctest 1
|
||||
julia> using DataStructures
|
||||
|
||||
julia> stabs .|> weight |> counter
|
||||
Accumulator{Int64, Int64} with 2 entries:
|
||||
0 => 1
|
||||
4 => 15
|
||||
|
||||
julia> function weight(i::Integer)
|
||||
Base.Fix2(weight, i)
|
||||
end
|
||||
weight (generic function with 3 methods)
|
||||
|
||||
julia> normalizers .|> weight(2) |> counter
|
||||
Accumulator{Int64, Int64} with 4 entries:
|
||||
0 => 1
|
||||
4 => 15
|
||||
5 => 18
|
||||
3 => 30
|
||||
|
||||
julia> [norm_x..., norm_y..., norm_z...] .|> weight(2) |> counter
|
||||
Accumulator{Int64, Int64} with 2 entries:
|
||||
5 => 18
|
||||
3 => 30
|
||||
|
||||
julia> [norm_x..., norm_y..., norm_z...] .|> weight(2) |> counter |> keys |> minimum
|
||||
3
|
||||
|
||||
```
|
||||
Code distance of the encoding is the minimum degree of the non-zero term in the normalizer's polynomial($B$) and not in the stabilizer's polynomial($A$).
|
||||
So the code distance of this encoding is $3$.
|
BIN
docs/src/img/bench_ref_optimized.jpg
Normal file
BIN
docs/src/img/bench_ref_optimized.jpg
Normal file
Binary file not shown.
After Width: | Height: | Size: 32 KiB |
BIN
docs/src/img/bench_ref_vs_aarref.jpg
Normal file
BIN
docs/src/img/bench_ref_vs_aarref.jpg
Normal file
Binary file not shown.
After Width: | Height: | Size: 72 KiB |
201
docs/src/index.md
Normal file
201
docs/src/index.md
Normal file
|
@ -0,0 +1,201 @@
|
|||
```@meta
|
||||
CurrentModule = QuantumLegos
|
||||
```
|
||||
|
||||
# QuantumLegos
|
||||
|
||||
Documentation for QuantumLegos.
|
||||
|
||||
All contents:
|
||||
|
||||
```@contents
|
||||
```
|
||||
|
||||
# Example
|
||||
|
||||
## CheckMatrix and defining Lego
|
||||
```jldoctest
|
||||
julia> using QuantumLegos
|
||||
|
||||
julia> stabilizers = pauliop.(["IIXXXX", "IIZZZZ", "ZIZZII", "IZZIZI", "IXXXII", "XIXIXI"])
|
||||
6-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("IIXXXX")
|
||||
pauliop("IIZZZZ")
|
||||
pauliop("ZIZZII")
|
||||
pauliop("IZZIZI")
|
||||
pauliop("IXXXII")
|
||||
pauliop("XIXIXI")
|
||||
|
||||
julia> cmat = checkmatrix(stabilizers)
|
||||
CheckMatrix with 6 generators, 6 legs:
|
||||
0 0 1 1 1 1 | 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 | 0 0 1 1 1 1
|
||||
0 0 0 0 0 0 | 1 0 1 1 0 0
|
||||
0 0 0 0 0 0 | 0 1 1 0 1 0
|
||||
0 1 1 1 0 0 | 0 0 0 0 0 0
|
||||
1 0 1 0 1 0 | 0 0 0 0 0 0
|
||||
|
||||
|
||||
julia> cmat.nlegs
|
||||
6
|
||||
|
||||
julia> cmat.ngens
|
||||
6
|
||||
|
||||
julia> cmat.cmat
|
||||
6×12 Matrix{Bool}:
|
||||
0 0 1 1 1 1 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 1 1 1 1
|
||||
0 0 0 0 0 0 1 0 1 1 0 0
|
||||
0 0 0 0 0 0 0 1 1 0 1 0
|
||||
0 1 1 1 0 0 0 0 0 0 0 0
|
||||
1 0 1 0 1 0 0 0 0 0 0 0
|
||||
|
||||
julia> # define lego
|
||||
|
||||
julia> lego = Lego(stabilizers)
|
||||
Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])
|
||||
|
||||
julia> lego.stabgens |> checkmatrix
|
||||
CheckMatrix with 6 generators, 6 legs:
|
||||
0 0 1 1 1 1 | 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 | 0 0 1 1 1 1
|
||||
0 0 0 0 0 0 | 1 0 1 1 0 0
|
||||
0 0 0 0 0 0 | 0 1 1 0 1 0
|
||||
0 1 1 1 0 0 | 0 0 0 0 0 0
|
||||
1 0 1 0 1 0 | 0 0 0 0 0 0
|
||||
|
||||
```
|
||||
|
||||
- [`pauliop`](@ref)
|
||||
- [`checkmatrix`](@ref) and [`CheckMatrix`](@ref)
|
||||
- [`Lego`](@ref)
|
||||
|
||||
## Defining and Updating State
|
||||
```jldoctest
|
||||
julia> using QuantumLegos
|
||||
|
||||
julia> stabilizers = pauliop.(["IIXXXX", "IIZZZZ", "ZIZZII", "IZZIZI", "IXXXII", "XIXIXI"])
|
||||
6-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("IIXXXX")
|
||||
pauliop("IIZZZZ")
|
||||
pauliop("ZIZZII")
|
||||
pauliop("IZZIZI")
|
||||
pauliop("IXXXII")
|
||||
pauliop("XIXIXI")
|
||||
|
||||
julia> lego = Lego(stabilizers)
|
||||
Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])
|
||||
|
||||
julia> # state with 1 lego, 0 leg
|
||||
|
||||
julia> st = State([lego, ], Tuple{LegoLeg, LegoLeg}[])
|
||||
State(Lego[Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])], Tuple{LegoLeg, LegoLeg}[], CheckMatrix(Bool[0 0 … 0 0; 0 0 … 1 1; … ; 0 1 … 0 0; 1 0 … 0 0], 6, 6))
|
||||
|
||||
julia> st.cmat.cmat
|
||||
6×12 Matrix{Bool}:
|
||||
0 0 1 1 1 1 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 1 1 1 1
|
||||
0 0 0 0 0 0 1 0 1 1 0 0
|
||||
0 0 0 0 0 0 0 1 1 0 1 0
|
||||
0 1 1 1 0 0 0 0 0 0 0 0
|
||||
1 0 1 0 1 0 0 0 0 0 0 0
|
||||
|
||||
julia> add_lego!(st, lego)
|
||||
State(Lego[Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")]), Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])], Tuple{LegoLeg, LegoLeg}[], CheckMatrix(Bool[0 0 … 0 0; 0 0 … 0 0; … ; 0 0 … 0 0; 0 0 … 0 0], 12, 12))
|
||||
|
||||
julia> st.cmat.cmat
|
||||
12×24 Matrix{Bool}:
|
||||
0 0 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 0 0 1 0 1 1 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 0 1 0 0 0 0 0 0 0
|
||||
0 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
1 0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1
|
||||
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1 1 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 0 1 0
|
||||
0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 1 0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0
|
||||
|
||||
julia> # state with 2 legos, 0 leg
|
||||
|
||||
julia> st2 = State([lego, lego], Tuple{LegoLeg, LegoLeg}[])
|
||||
State(Lego[Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")]), Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])], Tuple{LegoLeg, LegoLeg}[], CheckMatrix(Bool[0 0 … 0 0; 0 0 … 0 0; … ; 0 0 … 0 0; 0 0 … 0 0], 12, 12))
|
||||
|
||||
julia> st == st2
|
||||
true
|
||||
```
|
||||
|
||||
## 2 Lego 1 edge state
|
||||
```jldoctest
|
||||
julia> using QuantumLegos
|
||||
|
||||
julia> stabilizers = pauliop.(["IIXXXX", "IIZZZZ", "ZIZZII", "IZZIZI", "IXXXII", "XIXIXI"])
|
||||
6-element Vector{StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}}:
|
||||
pauliop("IIXXXX")
|
||||
pauliop("IIZZZZ")
|
||||
pauliop("ZIZZII")
|
||||
pauliop("IZZIZI")
|
||||
pauliop("IXXXII")
|
||||
pauliop("XIXIXI")
|
||||
|
||||
julia> lego = Lego(stabilizers)
|
||||
Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])
|
||||
|
||||
julia> state = State([lego, lego], edge.([((1, 3), (2, 3))]))
|
||||
State(Lego[Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")]), Lego{6}(6, StaticArraysCore.SVector{6, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("IIXXXX"), pauliop("IIZZZZ"), pauliop("ZIZZII"), pauliop("IZZIZI"), pauliop("IXXXII"), pauliop("XIXIXI")])], Tuple{LegoLeg, LegoLeg}[(LegoLeg(1, 3), LegoLeg(2, 3))], CheckMatrix(Bool[1 0 … 0 0; 0 1 … 0 0; … ; 0 0 … 1 1; 0 0 … 0 1], 10, 10))
|
||||
|
||||
julia> state.cmat
|
||||
CheckMatrix with 10 generators, 10 legs:
|
||||
1 0 1 0 1 0 0 0 0 0 | 0 0 0 0 0 0 0 0 0 0
|
||||
0 1 0 1 1 0 0 0 0 0 | 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 1 1 1 0 0 1 1 1 | 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 1 0 1 0 1 | 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 1 0 1 1 | 0 0 0 0 0 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 | 1 0 0 1 1 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 | 0 1 1 0 1 0 0 0 0 0
|
||||
0 0 0 0 0 0 0 0 0 0 | 0 0 1 1 1 0 0 1 1 1
|
||||
0 0 0 0 0 0 0 0 0 0 | 0 0 0 0 0 1 0 0 1 1
|
||||
0 0 0 0 0 0 0 0 0 0 | 0 0 0 0 0 0 1 1 0 1
|
||||
|
||||
|
||||
julia> pg = state.cmat |> generators |> GeneratedPauliGroup
|
||||
GeneratedPauliGroup{10}(StaticArraysCore.SVector{10, QuantumLegos.PauliOps.SinglePauliOp}[pauliop("XIXIXIIIII"), pauliop("IXIXXIIIII"), pauliop("IIXXXIIXXX"), pauliop("IIIIIXIXIX"), pauliop("IIIIIIXIXX"), pauliop("ZIIZZIIIII"), pauliop("IZZIZIIIII"), pauliop("IIZZZIIZZZ"), pauliop("IIIIIZIIZZ"), pauliop("IIIIIIZZIZ")], IterTools.Subsets{Vector{StaticArraysCore.SVector{N, QuantumLegos.PauliOps.SinglePauliOp} where N}}(StaticArraysCore.SVector{N, QuantumLegos.PauliOps.SinglePauliOp} where N[pauliop("XIXIXIIIII"), pauliop("IXIXXIIIII"), pauliop("IIXXXIIXXX"), pauliop("IIIIIXIXIX"), pauliop("IIIIIIXIXX"), pauliop("ZIIZZIIIII"), pauliop("IZZIZIIIII"), pauliop("IIZZZIIZZZ"), pauliop("IIIIIZIIZZ"), pauliop("IIIIIIZZIZ")]))
|
||||
|
||||
julia> pauliop("XIIXIXIIXI") in pg
|
||||
true
|
||||
|
||||
```
|
||||
|
||||
# Internal(how it works)
|
||||
|
||||
## Notes on Overall flow
|
||||
Details on [^1]
|
||||
- state is translated to a single check matrix
|
||||
- the size is ≤ $N \times 2N$ where $N$ is maximum number of lego logs.
|
||||
- any contraction can be performed on this single check matrix
|
||||
- if the check matrix can be represented as direct sum of matrices with $k N$ columns where $k ∈ ℕ$, then they are not contracted
|
||||
|
||||
### Construction of State
|
||||
Construction of `State` is completed by calling `State` constructor recursively.
|
||||
|
||||
1. Construct `State` without edge. Just adding legos. Checkmatrix is just a direct sum of each lego's checkmatrix
|
||||
2. Concatenate each edges. During this operation, self tracing of checkmatrix is evaluated.
|
||||
|
||||
Each constructor calls action function (which is a map from `State` to `State`).
|
||||
Therefore, action functions can be used both for direct construction of `State` and action application to `State` during the game.
|
||||
|
||||
# API
|
||||
|
||||
```@index
|
||||
```
|
||||
|
||||
```@autodocs
|
||||
Modules = [QuantumLegos]
|
||||
Pages = ["game.jl"]
|
||||
```
|
||||
|
||||
[^1]: [C. Cao and B. Lackey, ‘Approximate Bacon-Shor code and holography’, J. High Energ. Phys., vol. 2021, no. 5, p. 127, May 2021, doi: 10.1007/JHEP05(2021)127.](https://doi.org/10.1007/JHEP05(2021)127)
|
||||
|
46
docs/src/pauliops.md
Normal file
46
docs/src/pauliops.md
Normal file
|
@ -0,0 +1,46 @@
|
|||
# PauliOps
|
||||
|
||||
submodule
|
||||
|
||||
## Example
|
||||
```jldoctest
|
||||
julia> using QuantumLegos
|
||||
|
||||
julia> p = PauliOps.single_pauliop('I')
|
||||
I::SinglePauliOp = 0
|
||||
|
||||
julia> typeof(p)
|
||||
Enum QuantumLegos.PauliOps.SinglePauliOp:
|
||||
I = 0
|
||||
X = 1
|
||||
Y = 2
|
||||
Z = 3
|
||||
|
||||
julia> pauliop("IXYZ")
|
||||
4-element PauliOp:
|
||||
I::SinglePauliOp = 0
|
||||
X::SinglePauliOp = 1
|
||||
Y::SinglePauliOp = 2
|
||||
Z::SinglePauliOp = 3
|
||||
|
||||
julia> typeof(ans)
|
||||
SVector{4, SinglePauliOp} (alias for StaticArraysCore.SArray{Tuple{4}, QuantumLegos.PauliOps.SinglePauliOp, 1, 4})
|
||||
|
||||
julia> PauliOps.I * PauliOps.X
|
||||
X::SinglePauliOp = 1
|
||||
|
||||
julia> PauliOps.X * PauliOps.Z
|
||||
Y::SinglePauliOp = 2
|
||||
|
||||
julia> pauliop("IIX") .* pauliop("XIY")
|
||||
3-element PauliOp:
|
||||
X::SinglePauliOp = 1
|
||||
I::SinglePauliOp = 0
|
||||
Z::SinglePauliOp = 3
|
||||
```
|
||||
|
||||
## API
|
||||
```@autodocs
|
||||
Modules = [PauliOps]
|
||||
```
|
||||
|
Loading…
Add table
Add a link
Reference in a new issue