Skip to content

Commit

Permalink
Merge branch 'master' into coprime
Browse files Browse the repository at this point in the history
  • Loading branch information
Fe-r-oz authored Nov 5, 2024
2 parents 8860954 + 40924b8 commit 6f1967b
Show file tree
Hide file tree
Showing 40 changed files with 912 additions and 265 deletions.
8 changes: 8 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,14 @@ on:
branches: [master, main]
tags: ["*"]
pull_request:

concurrency:
# group by workflow and ref; the last slightly strange component ensures that for pull
# requests, we limit to 1 concurrent job, but for the master branch we don't
group: ${{ github.workflow }}-${{ github.ref }}-${{ github.ref != 'refs/heads/master' || github.run_number }}
# Cancel intermediate builds, but only if it is a pull request build.
cancel-in-progress: ${{ startsWith(github.ref, 'refs/pull/') }}

env:
PYTHON: ~
jobs:
Expand Down
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,6 @@ LocalPreferences.toml
*/.*swp
scratch/
*.cov
.vscode
.vscode
test/.CondaPkg/
docs/.CondaPkg/
16 changes: 16 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,22 @@

# News

## v0.9.14 - 2024-11-03

- **(fix)** `affectedqubits()` on `sMX`, `sMY`, and `sMR*`
- **(fix)** restrictive type-assert in `MixedDestabilizer` failing on views of tableaux
- Implementing additional named two-qubit gates: `sSQRTXX, sInvSQRTXX, sSQRTYY, sInvSQRTYY`

## v0.9.13 - 2024-10-30

- New error-correction group theory tools:
- `canonicalize_noncomm` function to find a generating set with minimal anticommutivity
- `SubsystemCodeTableau` data structure to represent the output of `canonicalize_noncomm`
- `commutify` function to find a commutative version of a non-commutative set of Paulis with minimal changes
- `matroid_parent` to, for set of Paulis that doesn't represent a state, find a version
that does.
- Implementing additional named two-qubit gates: `sSWAPCX, sInvSWAPCX, sCZSWAP, sCXSWAP, sISWAP, sInvISWAP, sSQRTZZ, sInvSQRTZZ`

## v0.9.12 - 2024-10-18

- Minor compat fixes for julia 1.11 in the handling of `hgp`
Expand Down
4 changes: 2 additions & 2 deletions Project.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
name = "QuantumClifford"
uuid = "0525e862-1e90-11e9-3e4d-1b39d7109de1"
authors = ["Stefan Krastanov <stefan@krastanov.org> and QuantumSavory community members"]
version = "0.9.12"
version = "0.9.14"

[deps]
Combinatorics = "861a8166-3701-5b0c-9a16-15d98fcdc6aa"
Expand Down Expand Up @@ -50,7 +50,7 @@ DocStringExtensions = "0.9"
Graphs = "1.9"
Hecke = "0.28, 0.29, 0.30, 0.31, 0.32, 0.33, 0.34"
HostCPUFeatures = "0.1.6"
ILog2 = "0.2.3"
ILog2 = "0.2.3, 1, 2"
InteractiveUtils = "1.9"
LDPCDecoders = "0.3.1"
LinearAlgebra = "1.9"
Expand Down
6 changes: 3 additions & 3 deletions docs/src/noisycircuits_mc.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ Import with `using QuantumClifford.Experimental.NoisyCircuits`.

This module enables the simulation of noisy Clifford circuits through a Monte Carlo method where the same circuit is evaluated multiple times with random errors interspersed through it as prescribed by a given error model.

Below is an example of a purification circuit. We first prepare the circuit we desire to use, including a noise model. `Quantikz.jl` was is used to visualize the circuit.
Below is an example of a purification circuit. We first prepare the circuit we desire to use, including a noise model. `Quantikz.jl` is used to visualize the circuit.

```@example 1
using QuantumClifford # hide
Expand Down Expand Up @@ -55,8 +55,8 @@ If you want to create a custom gate type (e.g. calling it `Operation`), you need
The `Symbol` is the status of the operation. Predefined statuses are kept in the `registered_statuses` list, but you can add more.
Be sure to expand this list if you want the trajectory simulators using your custom statuses to output all trajectories.

There is also [`applynoise!`](@ref) which is convenient wait to create a noise model that can then be plugged into the [`NoisyGate`](@ref) struct,
There is also [`applynoise!`](@ref) which is a convenient way to create a noise model that can then be plugged into the [`NoisyGate`](@ref) struct,
letting you reuse the predefined perfect gates and measurements.
However, you can also just make up your own noise operator simply by implementing [`applywstatus!`](@ref) for it.

You can also consult the [list of implemented operators](@ref noisycircuits_ops).
You can also consult the [list of implemented operators](@ref noisycircuits_ops).
37 changes: 36 additions & 1 deletion docs/src/references.bib
Original file line number Diff line number Diff line change
Expand Up @@ -403,6 +403,31 @@ @inproceedings{brown2013short
doi = {10.1109/ISIT.2013.6620245}
}

@article{RevModPhys.87.307,
title = {Quantum error correction for quantum memories},
author = {Terhal, Barbara M.},
journal = {Rev. Mod. Phys.},
volume = {87},
issue = {2},
pages = {307--346},
numpages = {40},
year = {2015},
month = {Apr},
publisher = {American Physical Society},
doi = {10.1103/RevModPhys.87.307},
url = {https://link.aps.org/doi/10.1103/RevModPhys.87.307}
}

@misc{goodenough2024bipartiteentanglementnoisystabilizer,
title={Bipartite entanglement of noisy stabilizer states through the lens of stabilizer codes},
author={Kenneth Goodenough and Aqil Sajjad and Eneet Kaur and Saikat Guha and Don Towsley},
year={2024},
eprint={2406.02427},
archivePrefix={arXiv},
primaryClass={quant-ph},
url={https://arxiv.org/abs/2406.02427},
}

@article{panteleev2021degenerate,
title = {Degenerate {{Quantum LDPC Codes With Good Finite Length Performance}}},
author = {Panteleev, Pavel and Kalachev, Gleb},
Expand Down Expand Up @@ -488,10 +513,20 @@ @article{anderson2014fault
publisher={APS}
}

@article{lin2024quantum,
title={Quantum two-block group algebra codes},
author={Lin, Hsiang-Ku and Pryadko, Leonid P},
journal={Physical Review A},
volume={109},
number={2},
pages={022407},
year={2024},
publisher={APS}
}

@article{wang2024coprime,
title={Coprime Bivariate Bicycle Codes and their Properties},
author={Wang, Ming and Mueller, Frank},
journal={arXiv preprint arXiv:2408.10001},
year={2024}
}

11 changes: 3 additions & 8 deletions ext/QuantumCliffordGPUExt/apply_noise.jl
Original file line number Diff line number Diff line change
@@ -1,16 +1,11 @@
using QuantumClifford: _div, _mod
using QuantumClifford: get_bitmask_idxs

#according to https://github.com/JuliaGPU/CUDA.jl/blob/ac1bc29a118e7be56d9edb084a4dea4224c1d707/test/core/device/random.jl#L33
#CUDA.jl supports calling rand() inside kernel
function applynoise!(frame::PauliFrameGPU{T},noise::UnbiasedUncorrelatedNoise,i::Int) where {T <: Unsigned}
p = noise.p
lowbit = T(1)
ibig = _div(T,i-1)+1
ismall = _mod(T,i-1)
ismallm = lowbit<<(ismall)

stab = frame.frame
xzs = tab(stab).xzs
xzs = tab(frame.frame).xzs
lowbit, ibig, ismall, ismallm = get_bitmask_idxs(xzs,i)
rows = size(stab, 1)

@run_cuda applynoise_kernel(xzs, p, ibig, ismallm, rows) rows
Expand Down
12 changes: 4 additions & 8 deletions ext/QuantumCliffordGPUExt/pauli_frames.jl
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
using QuantumClifford: get_bitmask_idxs

##############################
# sMZ
##############################
Expand All @@ -21,10 +23,7 @@ function apply!(frame::PauliFrameGPU{T}, op::QuantumClifford.sMZ) where {T <: Un
op.bit == 0 && return frame
i = op.qubit
xzs = frame.frame.tab.xzs
lowbit = T(1)
ibig = QuantumClifford._div(T,i-1)+1
ismall = QuantumClifford._mod(T,i-1)
ismallm = lowbit<<(ismall)
lowbit, ibig, ismall, ismallm = get_bitmask_idxs(xzs,i)
(@run_cuda apply_sMZ_kernel!(xzs, frame.measurements, op, ibig, ismallm, length(frame)) length(frame))
return frame
end
Expand Down Expand Up @@ -55,10 +54,7 @@ end
function apply!(frame::PauliFrameGPU{T}, op::QuantumClifford.sMRZ) where {T <: Unsigned} # TODO sMRX, sMRY
i = op.qubit
xzs = frame.frame.tab.xzs
lowbit = T(1)
ibig = QuantumClifford._div(T,i-1)+1
ismall = QuantumClifford._mod(T,i-1)
ismallm = lowbit<<(ismall)
lowbit, ibig, ismall, ismallm = get_bitmask_idxs(xzs,i)
(@run_cuda apply_sMRZ_kernel!(xzs, frame.measurements, op, ibig, ismallm, length(frame)) length(frame))
return frame
end
5 changes: 3 additions & 2 deletions ext/QuantumCliffordHeckeExt/QuantumCliffordHeckeExt.jl
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,15 @@ using DocStringExtensions
import QuantumClifford, LinearAlgebra
import Hecke: Group, GroupElem, AdditiveGroup, AdditiveGroupElem,
GroupAlgebra, GroupAlgebraElem, FqFieldElem, representation_matrix, dim, base_ring,
multiplication_table, coefficients, abelian_group, group_algebra
multiplication_table, coefficients, abelian_group, group_algebra, rand
import Nemo
import Nemo: characteristic, matrix_repr, GF, ZZ, lift

import QuantumClifford.ECC: AbstractECC, CSS, ClassicalCode,
hgp, code_k, code_n, code_s, iscss, parity_checks, parity_checks_x, parity_checks_z, parity_checks_xz,
two_block_group_algebra_codes, generalized_bicycle_codes, bicycle_codes
two_block_group_algebra_codes, generalized_bicycle_codes, bicycle_codes, check_repr_commutation_relation

include("util.jl")
include("types.jl")
include("lifted.jl")
include("lifted_product.jl")
Expand Down
28 changes: 24 additions & 4 deletions ext/QuantumCliffordHeckeExt/lifted_product.jl
Original file line number Diff line number Diff line change
Expand Up @@ -182,12 +182,32 @@ code_s(c::LPCode) = size(c.repr(zero(c.GA)), 1) * (size(c.A, 1) * size(c.B, 1) +
Two-block group algebra (2GBA) codes, which are a special case of lifted product codes
from two group algebra elements `a` and `b`, used as `1x1` base matrices.
Here is an example of a [[56, 28, 2]] 2BGA code from Table 2 of [lin2024quantum](@cite)
with direct product of `C₄ x C₂`.
```jldoctest
julia> import Hecke: group_algebra, GF, abelian_group, gens;
julia> GA = group_algebra(GF(2), abelian_group([14,2]));
julia> x = gens(GA)[1];
julia> s = gens(GA)[2];
julia> A = 1 + x^7
julia> B = 1 + x^7 + s + x^8 + s*x^7 + x
julia> c = two_block_group_algebra_codes(A,B);
julia> code_n(c), code_k(c)
(56, 28)
```
See also: [`LPCode`](@ref), [`generalized_bicycle_codes`](@ref), [`bicycle_codes`](@ref)
""" # TODO doctest example
"""
function two_block_group_algebra_codes(a::GroupAlgebraElem, b::GroupAlgebraElem)
A = reshape([a], (1, 1))
B = reshape([b], (1, 1))
LPCode(A, B)
LPCode([a;;], [b;;])
end

"""
Expand Down
15 changes: 15 additions & 0 deletions ext/QuantumCliffordHeckeExt/util.jl
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
"""
Checks the commutation relation between the left and right representation matrices
for two randomly-sampled elements `a` and `b` in the group algebra `ℱ[G]` with a general group `G`.
It verifies the commutation relation that states, `L(a)·R(b) = R(b)·L(a)`. This
property shows that matrices from the left and right representation sets commute
with each other, which is an important property related to the CSS orthogonality
condition.
"""
function check_repr_commutation_relation(GA::GroupAlgebra)
a, b = rand(GA), rand(GA)
# Check commutation relation: L(a)R(b) = R(b)L(a)
L_a = representation_matrix(a)
R_b = representation_matrix(b, :right)
return L_a * R_b == R_b * L_a
end
Loading

0 comments on commit 6f1967b

Please sign in to comment.